The JMicron JMB363 is a 2-port SATA + 1-port PATA controller chip often found embedded in motherboards and in low-cost add-on cards. The chip supports operating in IDE, AHCI, and RAID controller modes. Motherboard BIOSes allow choosing the operating mode, but add-on cards are stuck in RAID mode.
The problem with RAID mode is that standard AHCI drivers cannot be used. A JMicron-specific driver is available only for Windows. Some OSes (Linux, drivers/pci/quirks.c) set a PCI configuration register to put the controller into AHCI+IDE mode after booting and use standard drivers. Other OSes (Mac OS X) do nothing and can’t use the card.
I attempt to solve this problem by hacking the JMB363 option ROM to put the card into AHCI mode, with partial success. The two SATA ports work in OS X, including hot-plugging, but I could not get the parallel ATA enabled, and I had to bypass loading the option ROM (thus, can’t boot from the SATA ports anymore). The patched ROM might also be useful for other OSes that don’t have Linux-style PCI quirks.
- Original Option ROM 1.07.24
- Patch three uses of PCI configuration register 0xdf[1:0] to read 2′b10. This seems to put the controller in AHCI mode.
- Also patch two uses of 0xdf to read 1′b1 and writes 0xa1 to configuration register 0x41. This bypasses the option ROM and keeps the SATA ports enabled.
Hacking the Option ROM
I used the newest version of the option ROM (1.07.24) posted at JMicron’s FTP site. Some hints about the configuration of the JMB363 can be found in JMicron’s release notes, particularly about PCI configuration register 0xdf. The release notes hints at the existence of a newer 1.07.28, but it wasn’t posted. Linux’s drivers/pci/quirks.c gave some hints about the meaning of PCI configuration register 0x40-43.
Configuration Register 0xDF
PCI configuration register 0xdf seems to be intended for main BIOS to communicate its settings to the option ROM, rather than having a direct effect on the hardware. Bits [1:0] seem to indicate controller mode. Bits [7:6] and [5:4] look like they control two instances of the same thing because the code that parses them is structured the same way. The release notes say bit  is used to put the chip into “multi-function” mode with the option ROM disabled, which feels a little bit like a hack to me. Bits [3:2] don’t appear to be used.
|0||00||Default, RAID mode|
|0||01||IDE device (class 0101)|
|0||10||AHCI device (class 0106)|
|0||11||IDE device (class 0101)|
|1||00||RAID device (class 0104), no option ROM|
|1||01||AHCI device (class 0106), no option ROM|
|1||10||AHCI device (class 0106), no option ROM|
|1||11||AHCI device (class 0106), no option ROM|
It seems like bits [1:0] select the card mode (RAID, IDE, AHCI, IDE?), with the value 2′b11 probably not intended to be used (the option ROM code only distinguishes between 2′b00, 2′b01, and other).
Since setting df causes “jump out of Option ROM, do nothing” (See release notes for v1.03), it is no longer possible to boot from any disks attached to the chip.
In no case did setting 0xdf cause the JMB363 to become a multi-function device. I speculate its purpose is to disable the option ROM, allowing the main BIOS to set up the rest of the device configuration without interference.
- Register df is used by the option ROM code at offset 0x3517.
- Registers df[7:6] and df[5:4] are used at offsets 0x372d and 0x3756, respectively. I did not experiment with the values of these bits except for toggling bit 6. They seem important, causing PCI config register bits 0xed[5:2] and 0xcd[5:2] to be set when df[7:6] and df[5:4], respectively, is 2′b01 or 2′b10.
- Register df[1:0] is used in the option ROM at offset 0x3553, 0x3574, and 0x37c1
Configuration Register 0x40-43
These configuration registers seem to control the hardware directly. The option ROM sets them but doesn’t read them.
|43||Defaults to 0x80. Unknown purpose.|
|42||Seems to take values of 0xc2 or 0x82. Bits [1:0] depends on 0xdf[1:0], with a special case when 0xdf is set. Unknown purpose.|
|41||Bits [7:4] affect the SATA ports with [7:6] controlling SATA1, [5:4] controlling SATA0. Bits [3:0] unknown. Option ROM sets this to either 0xf1 or 0x51.|
|40||Bit 1 appears to control whether the second PCI function is enabled. Other bits unknown.|
Linux (drivers/pci/quirks.c) modifies this configuration register, which results in 0x80c2a1bf on my card. I tried modifying the option ROM to also configure register 0x40-43 to this value, but had many problems booting. Either I’m getting some of the other configuration bytes wrong or this value is intended only to be used after booting the system.
Only modifying register df[1:0] to value 2′b10 seems to put the controller into AHCI mode (with no IDE PCI function, but PATA drives are still detected by the option ROM). The option ROM loads, correctly reports connected drives, and allows booting from them. However, OS X does not detect hard drives that were detected by the option ROM at boot time. If SATA drives are not attached until after the option ROM loads, they are detected by the OS and can be hot-plugged. Therefore, I chose to set register df to cause the option ROM to quit without detecting drives. A side-effect is that without the option ROM, the computer can’t boot from the disks.
The problems with configuration register 0x40-43 are more problematic.
Linux sets register 0x41 to 0xa1, while the option ROM will set it to 0xf1 or 0x51. 0x51 appears to disable hot-plugging the disks on the SATA channels entirely. 0xa1 causes a hang for several minutes at boot, seemingly trying and failing to find a disk, while using 0xf1 boots normally. Trying with 0xb1 and 0xe1 shows the same behaviour as for 0xa1, but hangs only if a disk is not present on SATA0 or SATA1, respectively. Thus it seems like setting 0x41[7:6] or 0x41[5:4] to 2′b10 causes the option ROM to assert that a disk must be present at boot time for that channel. The hang does not occur if the option ROM is skipped by setting 0xdf, so I use 0xa1 to be closer to what Linux does, although I notice no other differences between 0xf1 and 0xa1.
Linux sets register 40 bit 2 (to enable the IDE port?). Trying to do that in the option ROM causes a several-minute hang during boot when loading the option ROM (again, seemingly waiting for a disk and giving up), even when a PATA disk is present. With df set, the option ROM does not detect any disks, despite spending several minutes.
- PATA not enabled because turning it on causes a hang during boot.
- Option ROM not enabled by setting df, so the disks are not bootable.
- SATA drives working in OS X with the standard AHCI driver, including hot-plugging.
PCICFG v1.24 (c) Copyright 1997,1998 Ralf Brown Modified by Datapath based on V1.19 ----------------------------------------------------------- PCI bus 04 device 00 function 00: Header Type 'non-bridge' (single-func) Vendor: 197B ??? Device: 2363 ??? Class: 01 disk Revision: 10 SubClass: 06 ??? ProgramI/F: 01 CommandReg: 0007 = I/O-on mem-on busmstr Status Reg: 0010 = CapList (fast) CacheLine: 08 Latency: 00 BIST: 00 SubsysVendor: 197B SubsysDevice: 2363 Base Addresses: (0) 00009001 = I/O base=00009000 len=8 (1) 00009401 = I/O base=00009400 len=4 (2) 00009801 = I/O base=00009800 len=8 (3) 00009C01 = I/O base=00009C00 len=4 (4) 0000A001 = I/O base=0000A000 len=16 (5) D9000000 = mem base=D9000000 len=512 CardBus: 00000000 ExpansionROM: 00000000 (64K,disabled) INTline: 0A INTpin: 01 MinGrant: 00 MaxLatency: 00 Device-Specific Data: 40: 80C2A1BD E4FF0808 40F00060 00000000 00110010 00008000 58: 000A2000 00036C11 10110000 00000000 00000000 00000000 70: 00000000 00000000 00000000 00000000 10000000 00000000 88: 00000000 40035001 00000000 00000000 00000000 00000000 A0: 00000000 00000000 00000000 00000000 00000000 00000000 B8: 00000000 80000000 00000000 00000000 00000000 00000000 D0: 80000018 1000001C 00EB0000 00000000 00000000 00000000 E8: 00000000 00000000 00100058 00000000 00000000 00100000 Capabilities List: ID @8C = 01 PCI Power Management PMC = PME#-D3hot DynClk = 0, PCI_PM version = 3 PMCSR = 0000, data-select=0 unknown/unimplemented state=D0 PMCSRX = -- -- -- -- Data = 00 ID @50 = 10 (unknown)