diff --git a/src/mainboard/chaintech/7kjd/7kjd.example-config b/src/mainboard/chaintech/7kjd/7kjd.example-config new file mode 100755 index 0000000000..001de69ef0 --- /dev/null +++ b/src/mainboard/chaintech/7kjd/7kjd.example-config @@ -0,0 +1,25 @@ + +# This will make a target directory of ./7kjd +# Note that this is RELATIVE TO WHERE YOU ARE WHEN YOU RUN THE +# CONFIG TOOL. Make it absolute if you like +target 7kjd + +mainboard chaintech/7kjd + +# Enable Serial Console for debugging +# It will come up at 115200,8n1 +option SERIAL_CONSOLE=1 +option TTYS0_BAUD=115200 +option DEFAULT_CONSOLE_LOGLEVEL=9 +option DEBUG=1 + +option RAMTEST=1 + +option USE_GENERIC_ROM=1 +option STD_FLASH=1 +option ROM_SIZE=262144 +option PAYLOAD_SIZE=196608 +option USE_ELF_BOOT=1 + +payload /home/filo.elf + diff --git a/src/mainboard/chaintech/7kjd/Config b/src/mainboard/chaintech/7kjd/Config index b14d42671f..e9a57f8538 100755 --- a/src/mainboard/chaintech/7kjd/Config +++ b/src/mainboard/chaintech/7kjd/Config @@ -4,11 +4,15 @@ mainboardinit cpu/i386/entry32.inc ldscript cpu/i386/entry16.lds ldscript cpu/i386/entry32.lds +mainboardinit cpu/k7/earlymtrr.inc + mainboardinit superio/via/vt8231/setup_serial.inc mainboardinit pc80/serial.inc mainboardinit arch/i386/lib/console.inc -mainboardinit cpu/k7/earlymtrr.inc +mainboardinit mainboard/chaintech/7kjd/smbus.inc +mainboardinit mainboard/chaintech/7kjd/mainboard_raminit.inc + mainboardinit southbridge/via/vt8231/ideconfig.inc northbridge amd/amd76x @@ -16,13 +20,18 @@ southbridge via/vt8231 keyboard pc80 +cpu p5 +cpu p6 cpu k7 object mainboard.o object irq_tables.o +option SMBUS_MEM_DEVICE_START=(0xa << 3) +option SMBUS_MEM_DEVICE_END=(SMBUS_MEM_DEVICE_START +3) +option SMBUS_MEM_DEVICE_INC=1 option HAVE_PIRQ_TABLE=1 option ENABLE_FIXED_AND_VARIABLE_MTRRS=1 option SUPERIO_DEVFN=0X88 option ENABLE_IDE_NATIVE_MODE=0 -#option FINAL_MAINBOARD_FIXUP=1 +option FINAL_MAINBOARD_FIXUP=1 diff --git a/src/mainboard/chaintech/7kjd/mainboard.c b/src/mainboard/chaintech/7kjd/mainboard.c index dc2118cfc9..2fc4e82851 100755 --- a/src/mainboard/chaintech/7kjd/mainboard.c +++ b/src/mainboard/chaintech/7kjd/mainboard.c @@ -1,6 +1,14 @@ +#include + void -mainboard_fixup() +mainboard_fixup(void) { - void southbridge_fixup(void); - southbridge_fixup(); +} + +void +final_mainboard_fixup(void) +{ + void final_southbridge_fixup(void); + + printk_info("CT 7KJD"); } diff --git a/src/mainboard/chaintech/7kjd/mainboard_raminit.inc b/src/mainboard/chaintech/7kjd/mainboard_raminit.inc new file mode 100755 index 0000000000..7bc57bb970 --- /dev/null +++ b/src/mainboard/chaintech/7kjd/mainboard_raminit.inc @@ -0,0 +1,140 @@ +jmp mainboard_raminit_out +#define DEFAULT_RAM_TRACE_SETTINGS 0 +#define USE_ECC_SDRAM 1 + + + + /* + * Routine: spd_to_dimm_side0 + * Arguments: %bl SMBUS_MEM_DEVICE + * + * Results: %edx DIMM register index + * + * Used: %ebx, %edx, %esp + * Trashed: %eflags + * Preserved: %eax, %ebx, %ecx, %esi, %edi, %ebp + * + * Effects: Dimms are not necessarily in the same order on the smbus + * as they are in chipset register indexes. This function + * maps the SMBUS device id to the logical index in + * the chipset, that is used to refer to a particular dimm. + */ +spd_to_dimm_side0: + movl %ebx, %edx + andl $0xff, %edx + subl $(SMBUS_MEM_DEVICE_START), %edx + /* 0 -> 0 */ + cmpl $0, %edx + jne 1f + movl $0, %edx + RETSP + /* 1 -> 6 */ +1: cmpl $1, %edx + jne 1f + movl $6, %edx + RETSP + /* 2 -> 4 */ +1: cmpl $2, %edx + jne 1f + movl $4, %edx + RETSP + /* 3 -> 2 */ +1: movl $2, %edx + RETSP + + + /* + * Routine: spd_to_dimm_side1 + * Arguments: %bl SMBUS_MEM_DEVICE + * + * Results: %edx DIMM register index + * + * Used: %ebx, %edx, %esp + * Trashed: %eflags + * Preserved: %eax, %ebx, %ecx, %esi, %edi, %ebp + * + * Effects: Dimms are not necessarily in the same order on the smbus + * as they are in chipset register indexes. This function + * maps the SMBUS device id to the logical index in + * the chipset, that is used to refer to a particular dimm. + */ +spd_to_dimm_side1: + movl %ebx, %edx + andl $0xff, %edx + subl $(SMBUS_MEM_DEVICE_START), %edx + /* 0 -> 1 */ + cmpl $0, %edx + jne 1f + movl $1, %edx + RETSP + /* 1 -> 7 */ +1: cmpl $1, %edx + jne 1f + movl $7, %edx + RETSP + /* 2 -> 5 */ +1: cmpl $2, %edx + jne 1f + movl $5, %edx + RETSP + /* 3 -> 3 */ +1: movl $3, %edx + RETSP + + +/* Set the calibration delay. These values may need to change per mainboard + * so we put them here. + */ + +sdram_software_calibration_delay: +#if DEFAULT_RAM_TRACE_SETTINGS + .byte 0x69, 0x00, 0x00, 0x6b +#else + .byte 0x69, 0x00, 0x00, 0x69 +#endif + +mainboard_constant_register_values: +#if DEFAULT_RAM_TRACE_SETTINGS +#else + .long 0x18c, 0x09052d05 + .long 0x190, 0x1b052d05 + .long 0x194, 0x2d052d05 + .long 0x198, 0x2d052d05 +#endif +#if USE_ECC_SDRAM + .long 0x48, (3 << 14)|(2 << 10)|(0 << 8)|(0 << 4)|(0 << 0) +#else + .long 0x48, 0 +#endif +mainboard_constant_register_values_end: + + + /* + * Routine: mainboard_verify_dram_timing + * Arguments: %edi the computed timing for the current dimm. + * Trashed: %eflags + * Results: cf clear + * %edi has a timing supported by this motherboard + * On Error: + * cf set + * %edi holds a timing not supported by this motherboard + * + * Effects: Verifies we can use the current dimm settings + * on the tyan 2466 motherboard. + * Currently the only potential problem is putting + * in unregistered SDRAM. + */ +mainboard_verify_dram_timing: + testl $(1<<27), %edi + jnz mainboard_verify_dram_timing_ok +mainboard_verify_dram_timing_error: + stc + jmp mainboard_verify_dram_timing_out +mainboard_verify_dram_timing_ok: + clc +mainboard_verify_dram_timing_out: + RET_LABEL(mainboard_verify_dram_timing) + +#undef DEFAULT_RAM_TRACE_SETTINGS +mainboard_raminit_out: + diff --git a/src/mainboard/chaintech/7kjd/smbus.inc b/src/mainboard/chaintech/7kjd/smbus.inc new file mode 100755 index 0000000000..3b52681434 --- /dev/null +++ b/src/mainboard/chaintech/7kjd/smbus.inc @@ -0,0 +1,201 @@ +/* Useful macros PCIBUS, and SMBUS functions for getting DRAM going. */ +/* courtesy Eric Biederman of linuxnetworx.com */ + +#define CS_WRITE_BYTE(addr, byte) \ + movl $addr, %eax ; \ + movl $byte, %edx ; \ + PCI_WRITE_CONFIG_BYTE + +#define CS_WRITE_WORD(addr, word) \ + movl $addr, %eax ; \ + movl $word, %ecx ; \ + PCI_WRITE_CONFIG_WORD + +#define CS_WRITE_LONG(addr, dword) \ + movl $addr, %eax ; \ + movl $dword, %ecx ; \ + PCI_WRITE_CONFIG_DWORD + +#define DEVFN(device, function) (((device) << 3) + (function)) +#ifndef CONFIG_ADDR +#define CONFIG_ADDR(bus,devfn,where) (((bus) << 16) | ((devfn) << 8) | (where)) +#endif + +/* jump around these subrs */ +jmp smbus_end + +/* generic SMB routines that work for many systems. The only one that might + * not work is the enable_smbus. + * you have to define PM_FUNCTION for this to work. + */ +#define SMBUS_IO_BASE 0xf00 +#define SMBHSTSTAT 0 +#define SMBHSTCTL 2 +#define SMBHSTCMD 3 +#define SMBHSTADD 4 +#define SMBHSTDAT0 5 +#define SMBHSTDAT1 6 +#define SMBBLKDAT 7 + + /* + * Routine: setup_smbus + * Arguments: none + * Results: none + * Trashed: eax, edx + * Effects: The smbus is enabled + */ +setup_smbus: + xor %eax,%eax + movl $(SMBUS_IO_BASE +SMBHSTSTAT), %edx + outb %al, %dx + RET_LABEL(setup_smbus) + +#define SMBUS_MEM_DEVICE_0 (0xa << 3) +#define SMBUS_MEM_DEVICE_1 (SMBUS_MEM_DEVICE_0 +1) +#define SMBUS_MEM_DEVICE_2 (SMBUS_MEM_DEVICE_0 +2) +#define SMBUS_MEM_DEVICE_3 (SMBUS_MEM_DEVICE_0 +3) +#define SMBUS_SPD 0 + +#if SMBUS_SPD + /* + * Routine: smbus_wait_until_ready + * Arguments: none + * Results: none + * Trashed: eax, edx + * Effects: Upon return the smbus is ready to accept commands + */ +smbus_wait_until_ready: + movl $(SMBUS_IO_BASE + SMBHSTSTAT), %edx +1: inb %dx, %al + testb $1, %al + jnz 1b + RET_LABEL(smbus_wait_until_ready) + + /* + * Routine: smbus_wait_until_done + * Arguments: none + * Results: none + * Trashed: eax, edx + * Effects: Upon return the smbus has completed it's most recent transation + */ +smbus_wait_until_done: + movl $(SMBUS_IO_BASE + SMBHSTSTAT), %edx +1: inb %dx, %al + testb $1, %al + jnz 1b +2: testb $0xFE, %al + jnz 3f + inb %dx, %al + testb $0xFE, %al + jz 2b +3: RET_LABEL(smbus_wait_until_done) +#endif + + /* + * Routine: smbus_read_byte + * Arguments: %esp return address + * %bl device on the smbus to read from + * %bh address on the smbus to read + * + * Results: zf clear + * byte read %eax + * On Error: + * zf set + * %eax trashed + * + * Trashed: %edx, %eax + * Effects: reads a byte off of the smbus + */ + +#define SMBUS_READ_BYTE(device, address) \ + movl $( (device) | ((address) << 8)), %ebx ; \ + CALLSP(smbus_read_byte) + +#if SMBUS_SPD +smbus_read_byte: + /* poll until the smbus is ready for commands */ + CALL_LABEL(smbus_wait_until_ready) + + /* clear any lingering errors, so that the transaction will run */ + movl $(SMBUS_IO_BASE + SMBHSTSTAT), %edx + inb %dx, %al + outb %al, %dx + + /* set the device I'm talking to */ + movl $(SMBUS_IO_BASE + SMBHSTADD), %edx + movb %bl /* device */, %al + shlb $1, %al + orb $1, %al + outb %al, %dx + + /* set the command address... */ + movl $(SMBUS_IO_BASE + SMBHSTCMD), %edx + movb %bh /* address */, %al + outb %al, %dx + + /* clear the data byte */ + movl $(SMBUS_IO_BASE + SMBHSTDAT0), %edx + xorl %eax, %eax + outb %al, %dx + + /* start a byte read, with interrupts disabled */ + movl $(SMBUS_IO_BASE + SMBHSTCTL), %edx + movl $((0x2 << 2) | (1 << 6)), %eax + outb %al, %dx + + /* poll for transaction completion */ + CALL_LABEL(smbus_wait_until_done) + + /* read the results and see if we succeded */ + movl $(SMBUS_IO_BASE + SMBHSTSTAT), %edx + inb %dx, %al + testb $0x02, %al + jz 1f + movl $(SMBUS_IO_BASE + SMBHSTDAT0), %edx + inb %dx, %al +1: + RETSP +#else + /* This table and code are used because I could not get + the smbus to work, so the table below is for dimm ram + that is compatable to the Samsung M383L3313BT1-B0. + The routine below simulates an smbus read for address + 0x50 and 0x51. + */ +smbus_spd_table: +.byte 0x80, 0x08, 0x07, 0x0c, 0x0a, 0x02, 0x48, 0x00 +.byte 0x04, 0x75, 0x75, 0x02, 0x80, 0x08, 0x08, 0x01 +.byte 0x0e, 0x04, 0x0c, 0x01, 0x02, 0x26, 0x00, 0xa0 +.byte 0x75, 0x00, 0x00, 0x50, 0x3c, 0x50, 0x2d, 0x20 +.byte 0x90, 0x90, 0x50, 0x50, 0x00, 0x00, 0x00, 0x00 +smbus_spd_table_end: + +smbus_read_byte: + /* test for a valid device */ + cmpb $0x50, %bl + jz srb10; + cmpb $0x51, %bl + jnz srb_err +srb10: + /* get the index in eax */ + xorl %eax, %eax + movb %bh, %al + /* load the byte from the table */ + movl $smbus_spd_table, %edx + addl %eax, %edx + movb 0(%edx), %al + cmpl $smbus_spd_table_end, %edx + jb srb20 + movb $0, %al + /* clear the zero flag */ +srb20: + testl %edx, %edx + RETSP +srb_err: + xorl %eax, %eax + RETSP +#endif + +smbus_end: +CALL_LABEL(setup_smbus) +