summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorsimokawa <simokawa@FreeBSD.org>2003-02-14 03:09:59 +0000
committersimokawa <simokawa@FreeBSD.org>2003-02-14 03:09:59 +0000
commitee568cc79e5011ade30e0ab18dc592ee3152cbca (patch)
treebbc98a7fc29be58f158a2ae39fc5d197eacaf219 /sys
parentd8fb26b1c6097066a057362bdf7ad3d5e61c349b (diff)
downloadFreeBSD-src-ee568cc79e5011ade30e0ab18dc592ee3152cbca.zip
FreeBSD-src-ee568cc79e5011ade30e0ab18dc592ee3152cbca.tar.gz
- Though I got a feedback from the originator of kern/48129 that the
previous revision fixed the panic, I found the problem exits in another part of the function by investigating the crom dump sent by him. The search was started in the middle of bus info block and the routine misunderstood the EUI64 as a crom entry. This problem is fixed. PR: kern/48129 Fix incorrect type mask included in a logical unit number and check the validity of the lun.
Diffstat (limited to 'sys')
-rw-r--r--sys/dev/firewire/sbp.c30
1 files changed, 18 insertions, 12 deletions
diff --git a/sys/dev/firewire/sbp.c b/sys/dev/firewire/sbp.c
index 079ea74..f8bc93b 100644
--- a/sys/dev/firewire/sbp.c
+++ b/sys/dev/firewire/sbp.c
@@ -474,7 +474,7 @@ END_DEBUG
reg = crom_search_key(&cc, CROM_LUN);
if (reg == NULL)
break;
- lun = reg->val & 0xff;
+ lun = reg->val & 0xffff;
SBP_DEBUG(0)
printf("target %d lun %d found\n", target->target_id, lun);
END_DEBUG
@@ -482,10 +482,11 @@ END_DEBUG
maxlun = lun;
crom_next(&cc);
}
- target->num_lun = maxlun + 1;
- if (maxlun < 0) {
+ if (maxlun < 0)
printf("no lun found!\n");
- }
+ if (maxlun >= SBP_NUM_LUNS)
+ maxlun = SBP_NUM_LUNS;
+ target->num_lun = maxlun + 1;
target->luns = (struct sbp_dev *) malloc(
sizeof(struct sbp_dev) * target->num_lun,
M_SBP, M_NOWAIT | M_ZERO);
@@ -501,13 +502,17 @@ END_DEBUG
reg = crom_search_key(&cc, CROM_LUN);
if (reg == NULL)
break;
- lun = reg->val & 0xff;
+ lun = reg->val & 0xffff;
+ if (lun >= SBP_NUM_LUNS) {
+ printf("too large lun %d\n", lun);
+ continue;
+ }
target->luns[lun].status = SBP_DEV_RESET;
- target->luns[lun].type = (reg->val & 0x0f00) >> 16;
+ target->luns[lun].type = (reg->val & 0xf0000) >> 16;
crom_next(&cc);
- }
- return target;
-}
+ }
+ return target;
+ }
static void
sbp_get_text_leaf(struct fw_device *fwdev, int key, char *buf, int len)
@@ -519,9 +524,10 @@ sbp_get_text_leaf(struct fw_device *fwdev, int key, char *buf, int len)
u_int32_t *src, *dst;
chdr = (struct csrhdr *)&fwdev->csrrom[0];
- creg = (struct csrreg *)chdr;
- creg += chdr->info_len;
- for( i = chdr->info_len + 4; i <= fwdev->rommax - 4; i+=4){
+ /* skip crom header, bus info and root directory */
+ creg = (struct csrreg *)chdr + chdr->info_len + 2;
+ /* search unitl the one before the last. */
+ for (i = chdr->info_len + 2; i < fwdev->rommax / 4; i++) {
if((creg++)->key == key){
found = 1;
break;
OpenPOWER on IntegriCloud