Index: sys/dev/ic/aac.c
===================================================================
RCS file: /cvsroot/src/sys/dev/ic/aac.c,v
retrieving revision 1.40
diff -u -r1.40 aac.c
--- sys/dev/ic/aac.c	8 Jun 2008 12:43:51 -0000	1.40
+++ sys/dev/ic/aac.c	29 Sep 2008 13:33:19 -0000
@@ -458,10 +458,8 @@
 		    (sc->sc_if.aif_send_command != NULL)) {
 			sc->sc_quirks |= AAC_QUIRK_NEW_COMM;
 		}
-#ifdef notyet
 		if (opts & AAC_SUPPORTED_64BIT_ARRAYSIZE)
 			sc->sc_quirks |= AAC_QUIRK_ARRAY_64BIT;
-#endif
 	}
 
 	sc->sc_max_fibs = (sc->sc_quirks & AAC_QUIRK_256FIBS) ? 256 : 512;
@@ -538,6 +536,16 @@
 
 	sc->sc_max_fibs_alloc = PAGE_SIZE / sc->sc_max_fib_size;
 
+	if (sc->sc_max_fib_size > sizeof(struct aac_fib)) {
+		sc->sc_quirks |= AAC_QUIRK_RAW_IO;
+		aprint_debug_dev(&sc->sc_dv, "Enable raw I/O\n");
+	}
+	if ((sc->sc_quirks & AAC_QUIRK_RAW_IO) &&
+	    (sc->sc_quirks & AAC_QUIRK_ARRAY_64BIT)) {
+		sc->sc_quirks |= AAC_QUIRK_LBA_64BIT;
+		aprint_normal_dev(&sc->sc_dv, "Enable 64-bit array support\n");
+	}
+
 	return (0);
 }
 
@@ -632,10 +640,8 @@
 	 */
 	ip = &sc->sc_common->ac_init;
 	ip->InitStructRevision = htole32(AAC_INIT_STRUCT_REVISION);
-	if (sc->sc_max_fib_size > sizeof(struct aac_fib)) {
+	if (sc->sc_quirks & AAC_QUIRK_RAW_IO)
 		ip->InitStructRevision = htole32(AAC_INIT_STRUCT_REVISION_4);
-		sc->sc_quirks |= AAC_QUIRK_RAW_IO;
-	}
 	ip->MiniPortRevision = htole32(AAC_INIT_STRUCT_MINIPORT_REVISION);
 
 	ip->AdapterFibsPhysicalAddress = htole32(sc->sc_common_seg.ds_addr +
@@ -812,6 +818,7 @@
 	struct aac_mntinforesponse mir;
 	struct aac_drive *hd;
 	u_int16_t rsize;
+	size_t ersize;
 	int i;
 
 	/*
@@ -824,7 +831,14 @@
 		 * Request information on this container.
 		 */
 		memset(&mi, 0, sizeof(mi));
-		mi.Command = htole32(VM_NameServe);
+		/* use 64-bit LBA if enabled */
+		if (sc->sc_quirks & AAC_QUIRK_LBA_64BIT) {
+			mi.Command = htole32(VM_NameServe64);
+			ersize = sizeof(mir);
+		} else {
+			mi.Command = htole32(VM_NameServe);
+			ersize = sizeof(mir) - sizeof(mir.MntTable[0].CapacityHigh);
+		}
 		mi.MntType = htole32(FT_FILESYS);
 		mi.MntCount = htole32(i);
 		if (aac_sync_fib(sc, ContainerCommand, 0, &mi, sizeof(mi), &mir,
@@ -832,9 +846,9 @@
 			aprint_error_dev(&sc->sc_dv, "error probing container %d\n", i);
 			continue;
 		}
-		if (rsize != sizeof(mir)) {
+		if (rsize != ersize) {
 			aprint_error_dev(&sc->sc_dv, "container info response wrong size "
-			    "(%d should be %zu)\n", rsize, sizeof(mir));
+			    "(%d should be %zu)\n", rsize, ersize);
 			continue;
 		}
 
@@ -848,6 +862,9 @@
 
 		hd->hd_present = 1;
 		hd->hd_size = le32toh(mir.MntTable[0].Capacity);
+		if (sc->sc_quirks & AAC_QUIRK_LBA_64BIT)
+			hd->hd_size += (u_int64_t)
+			    le32toh(mir.MntTable[0].CapacityHigh) << 32;
 		hd->hd_devtype = le32toh(mir.MntTable[0].VolType);
 		hd->hd_size &= ~0x1f;
 		sc->sc_nunits++;
Index: sys/dev/ic/aacreg.h
===================================================================
RCS file: /cvsroot/src/sys/dev/ic/aacreg.h,v
retrieving revision 1.12
diff -u -r1.12 aacreg.h
--- sys/dev/ic/aacreg.h	8 Sep 2008 23:36:54 -0000	1.12
+++ sys/dev/ic/aacreg.h	29 Sep 2008 13:33:19 -0000
@@ -535,6 +535,7 @@
 		u_int32_t pad[8];
 	} ObjExtension;
 	u_int32_t AlterEgoId;
+	u_int32_t CapacityHigh; /* Only if VM_NameServe64 */
 } __packed;
 
 struct aac_mntinfo {
Index: sys/dev/ic/aacvar.h
===================================================================
RCS file: /cvsroot/src/sys/dev/ic/aacvar.h,v
retrieving revision 1.12
diff -u -r1.12 aacvar.h
--- sys/dev/ic/aacvar.h	28 Apr 2008 20:23:48 -0000	1.12
+++ sys/dev/ic/aacvar.h	29 Sep 2008 13:33:19 -0000
@@ -160,6 +160,7 @@
 #define AAC_QUIRK_NEW_COMM	(1 << 11)	/* New comm. i/f supported */
 #define AAC_QUIRK_RAW_IO	(1 << 12)	/* Raw I/O interface */
 #define AAC_QUIRK_ARRAY_64BIT	(1 << 13)	/* 64-bit array size */
+#define AAC_QUIRK_LBA_64BIT	(1 << 14)	/* 64-bit LBA support */
 
 
 /*
@@ -284,7 +285,7 @@
 struct aac_drive {
 	u_int	hd_present;
 	u_int	hd_devtype;
-	u_int	hd_size;
+	u_int64_t	hd_size;
 };
 
 /*
Index: sys/dev/ic/ld_aac.c
===================================================================
RCS file: /cvsroot/src/sys/dev/ic/ld_aac.c,v
retrieving revision 1.21
diff -u -r1.21 ld_aac.c
--- sys/dev/ic/ld_aac.c	9 Sep 2008 12:45:39 -0000	1.21
+++ sys/dev/ic/ld_aac.c	29 Sep 2008 13:33:19 -0000
@@ -63,7 +63,7 @@
 
 static void	ld_aac_attach(device_t, device_t, void *);
 static void	ld_aac_intr(struct aac_ccb *);
-static int	ld_aac_dobio(struct ld_aac_softc *, void *, int, int, int,
+static int	ld_aac_dobio(struct ld_aac_softc *, void *, int, daddr_t, int,
 			     struct buf *);
 static int	ld_aac_dump(struct ld_softc *, void *, int, int);
 static int	ld_aac_match(device_t, cfdata_t, void *);
@@ -106,7 +106,7 @@
 }
 
 static int
-ld_aac_dobio(struct ld_aac_softc *sc, void *data, int datasize, int blkno,
+ld_aac_dobio(struct ld_aac_softc *sc, void *data, int datasize, daddr_t blkno,
 	     int dowrite, struct buf *bp)
 {
 	struct aac_blockread_response *brr;
@@ -145,7 +145,37 @@
 	    AAC_FIBSTATE_REXPECTED | AAC_FIBSTATE_NORM |
 	    AAC_FIBSTATE_ASYNC | AAC_FIBSTATE_FAST_RESPONSE );
 
-	if ((aac->sc_quirks & AAC_QUIRK_SG_64BIT) == 0) {
+	if (aac->sc_quirks & AAC_QUIRK_RAW_IO) {
+		struct aac_raw_io *raw;
+		struct aac_sg_entryraw *sge;
+		struct aac_sg_tableraw *sgt;
+
+		raw = (struct aac_raw_io *)&fib->data[0];
+		fib->Header.Command = htole16(RawIo);
+		raw->BlockNumber = htole64(blkno);
+		raw->ByteCount = htole32(datasize);
+		raw->ContainerId = htole16(sc->sc_hwunit);
+		raw->BpTotal = 0;
+		raw->BpComplete = 0;
+		size = sizeof(struct aac_raw_io);
+		sgt = &raw->SgMapRaw;
+		raw->Flags = (dowrite ? 0 : 1);
+
+		xfer = ac->ac_dmamap_xfer;
+		sgt->SgCount = xfer->dm_nsegs;
+		sge = sgt->SgEntryRaw;
+
+		for (i = 0; i < xfer->dm_nsegs; i++, sge++) {
+			sge->SgAddress = htole64(xfer->dm_segs[i].ds_addr);
+			sge->SgByteCount = htole32(xfer->dm_segs[i].ds_len);
+			sge->Next = 0;
+			sge->Prev = 0;
+			sge->Flags = 0;
+		}
+		size += xfer->dm_nsegs * sizeof(struct aac_sg_entryraw);
+		size = sizeof(fib->Header) + size;
+		fib->Header.Size = htole16(size);
+	} else if ((aac->sc_quirks & AAC_QUIRK_SG_64BIT) == 0) {
 		struct aac_blockread *br;
 		struct aac_blockwrite *bw;
 		struct aac_sg_entry *sge;
@@ -188,7 +218,7 @@
 		}
 
 		size += xfer->dm_nsegs * sizeof(struct aac_sg_entry);
-		size = htole16(sizeof(fib->Header) + size);
+		size = sizeof(fib->Header) + size;
 		fib->Header.Size = htole16(size);
 	} else {
 		struct aac_blockread64 *br;
@@ -240,7 +270,7 @@
 			    (u_long)xfer->dm_segs[i].ds_len));
 		}
 		size += xfer->dm_nsegs * sizeof(struct aac_sg_entry64);
-		size = htole16(sizeof(fib->Header) + size);
+		size = sizeof(fib->Header) + size;
 		fib->Header.Size = htole16(size);
 	}