summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Sevakis <jethead71@rockbox.org>2007-03-11 13:59:31 +0000
committerMichael Sevakis <jethead71@rockbox.org>2007-03-11 13:59:31 +0000
commit89a38d4273a9ef6f7e2d46876ddfe5ce8cee10da (patch)
treec3707e992cf53ddf71410e75eab4a35ed97defcc
parent04ea446edc56d0891f458ffa8f2b0e2616e443df (diff)
downloadrockbox-89a38d4273a9ef6f7e2d46876ddfe5ce8cee10da.tar.gz
rockbox-89a38d4273a9ef6f7e2d46876ddfe5ce8cee10da.zip
iAudio X5: Enable reading of DS2411 serial number. See it under System|Debug|View HW info.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@12723 a1c6a512-1295-4272-9138-f99709370657
-rw-r--r--apps/debug_menu.c38
-rw-r--r--firmware/SOURCES1
-rw-r--r--firmware/export/ds2411.h48
-rw-r--r--firmware/target/coldfire/iaudio/x5/ds2411-x5.c206
4 files changed, 290 insertions, 3 deletions
diff --git a/apps/debug_menu.c b/apps/debug_menu.c
index 13e0046334..6b5194f147 100644
--- a/apps/debug_menu.c
+++ b/apps/debug_menu.c
@@ -81,6 +81,9 @@
#ifdef IRIVER_H300_SERIES
#include "pcf50606.h" /* for pcf50606_read */
#endif
+#ifdef IAUDIO_X5
+#include "ds2411.h"
+#endif
/*---------------------------------------------------*/
/* SPECIAL DEBUG STUFF */
@@ -535,8 +538,9 @@ static bool dbg_hw_info(void)
#elif CONFIG_CPU == MCF5249 || CONFIG_CPU == MCF5250
char buf[32];
unsigned manu, id; /* flash IDs */
- bool got_id; /* flag if we managed to get the flash IDs */
+ int got_id; /* flag if we managed to get the flash IDs */
int oldmode; /* saved memory guard mode */
+ int line = 0;
oldmode = system_memory_guard(MEMGUARD_NONE); /* disable memory guard */
@@ -551,13 +555,41 @@ static bool dbg_hw_info(void)
lcd_setfont(FONT_SYSFIXED);
lcd_clear_display();
- lcd_puts(0, 0, "[Hardware info]");
+ lcd_puts(0, line++, "[Hardware info]");
if (got_id)
snprintf(buf, 32, "Flash: M=%04x D=%04x", manu, id);
else
snprintf(buf, 32, "Flash: M=???? D=????"); /* unknown, sorry */
- lcd_puts(0, 1, buf);
+ lcd_puts(0, line++, buf);
+
+#ifdef IAUDIO_X5
+ {
+ struct ds2411_id id;
+
+ line++;
+ lcd_puts(0, line++, "Serial Number:");
+
+ got_id = ds2411_read_id(&id);
+
+ if (got_id == DS2411_OK)
+ {
+ snprintf(buf, 32, " FC=%02x", (unsigned)id.family_code);
+ lcd_puts(0, line++, buf);
+ snprintf(buf, 32, " ID=%02X %02X %02X %02X %02X %02X",
+ (unsigned)id.uid[0], (unsigned)id.uid[1], (unsigned)id.uid[2],
+ (unsigned)id.uid[3], (unsigned)id.uid[4], (unsigned)id.uid[5]);
+ lcd_puts(0, line++, buf);
+ snprintf(buf, 32, " CRC=%02X", (unsigned)id.crc);
+ lcd_puts(0, line++, buf);
+ }
+ else
+ {
+ snprintf(buf, 32, "READ ERR=%d", got_id);
+ lcd_puts(0, line++, buf);
+ }
+ }
+#endif
lcd_update();
diff --git a/firmware/SOURCES b/firmware/SOURCES
index 2d2296a439..945f400243 100644
--- a/firmware/SOURCES
+++ b/firmware/SOURCES
@@ -364,6 +364,7 @@ target/coldfire/iaudio/system-iaudio.c
target/coldfire/iaudio/usb-iaudio.c
target/coldfire/iaudio/x5/backlight-x5.c
target/coldfire/iaudio/x5/button-x5.c
+target/coldfire/iaudio/x5/ds2411-x5.c
target/coldfire/iaudio/x5/lcd-as-x5.S
target/coldfire/iaudio/x5/lcd-x5.c
target/coldfire/iaudio/x5/m5636-x5.c
diff --git a/firmware/export/ds2411.h b/firmware/export/ds2411.h
new file mode 100644
index 0000000000..c55579cba5
--- /dev/null
+++ b/firmware/export/ds2411.h
@@ -0,0 +1,48 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2007 by Michael Sevakis
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef _DS2411_H_
+#define _DS2411_H_
+
+#include <stdbool.h>
+
+/*
+ * Byte 0: 8-bit family code (always 01h)
+ * Bytes 1-6: 48-bit serial number
+ * Byte 7: 8-bit CRC code
+ */
+struct ds2411_id
+{
+ unsigned char family_code;
+ unsigned char uid[6];
+ unsigned char crc;
+} __attribute__((packed));
+
+extern int ds2411_read_id(struct ds2411_id *id);
+
+/* return values */
+enum ds2411_id_return_codes
+{
+ DS2411_NO_PRESENCE = -3,
+ DS2411_INVALID_FAMILY_CODE,
+ DS2411_INVALID_CRC,
+ DS2411_OK = 0,
+};
+
+#endif /* _DS2411_H_ */
diff --git a/firmware/target/coldfire/iaudio/x5/ds2411-x5.c b/firmware/target/coldfire/iaudio/x5/ds2411-x5.c
new file mode 100644
index 0000000000..a8b2ae705c
--- /dev/null
+++ b/firmware/target/coldfire/iaudio/x5/ds2411-x5.c
@@ -0,0 +1,206 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2007 by Michael Sevakis
+ *
+ * All files in this archive are subject to the GNU General Public License.
+ * See the file COPYING in the source tree root for full license agreement.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "config.h"
+#include "system.h"
+#include "cpu.h"
+#include "ds2411.h"
+#include "logf.h"
+
+/* Delay factor that depends on CPU frequency */
+static unsigned int ds2411_delay_factor = 0;
+
+#define DS2411_BIT (1 << 22)
+
+/* Delay the specified number of microseconds - plus a tiny bit */
+#define DELAY(uS) \
+ asm volatile( \
+ "move.l %[x], %%d0 \n" \
+ "mulu.l %[factor], %%d0 \n" \
+ "1: \n" \
+ "subq.l #1, %%d0 \n" \
+ "bhi.s 1b \n" \
+ : : [factor]"d"(ds2411_delay_factor), [x]"d"(uS) : "d0");
+
+/* Calculate the CRC of a byte */
+static unsigned char ds2411_calc_crc(unsigned char byte)
+{
+ /* POLYNOMIAL = X^8 + X^5 + X^4 + 1 */
+ static const unsigned char eor[8] =
+ {
+ 0x5e, /* 01011110 */
+ 0xbc, /* 10111100 */
+ 0x61, /* 01100001 */
+ 0xc2, /* 11000010 */
+ 0x9d, /* 10011101 */
+ 0x23, /* 00100011 */
+ 0x46, /* 01000110 */
+ 0x8c, /* 10001100 */
+ };
+
+ unsigned char crc = 0;
+ int i = 0;
+
+ do
+ {
+ if (byte & (1 << i))
+ crc ^= eor[i];
+ }
+ while (++i < 8);
+
+ return crc;
+} /* ds2411_calc_crc */
+
+/* Write a byte to the DS2411 - LSb first */
+static void ds2411_write_byte(unsigned char data)
+{
+ int i = 0;
+
+ do
+ {
+ if (data & 0x01)
+ {
+ /* Write a "1": Hold line low, then leave line pulled up and wait
+ out the remainder of Tslot */
+ or_l(DS2411_BIT, &GPIO_ENABLE);
+ DELAY(6);
+ and_l(~DS2411_BIT, &GPIO_ENABLE);
+ DELAY(60);
+ }
+ else
+ {
+ /* Write a "0": Hold line low, then leave line pulled up and wait
+ out the remainder of Tslot which is just Trec */
+ or_l(DS2411_BIT, &GPIO_ENABLE);
+ DELAY(60);
+ and_l(~DS2411_BIT, &GPIO_ENABLE);
+ DELAY(6);
+ }
+
+ data >>= 1;
+ }
+ while (++i < 8);
+} /* ds2411_write_byte */
+
+/* Read a byte from the DS2411 - LSb first */
+static unsigned char ds2411_read_byte(void)
+{
+ int i = 0;
+ unsigned data = 0;
+
+ do
+ {
+ /* Hold line low to begin bit read: Tf + Trl */
+ or_l(DS2411_BIT, &GPIO_ENABLE);
+ DELAY(6);
+
+ /* Set line high and delay before sampling within the master
+ sampling window: Tmsr - max 15us from Trl start */
+ and_l(~DS2411_BIT, &GPIO_ENABLE);
+ DELAY(9);
+
+ /* Sample data line */
+ if ((GPIO_READ & DS2411_BIT) != 0)
+ data |= 1 << i;
+
+ /* Wait out the remainder of Tslot */
+ DELAY(60);
+ }
+ while (++i < 8);
+
+ return data;
+} /* ds2411_read_byte */
+
+/*
+ * Byte 0: 8-bit family code (01h)
+ * Bytes 1-6: 48-bit serial number
+ * Byte 7: 8-bit CRC code
+ */
+int ds2411_read_id(struct ds2411_id *id)
+{
+ int i;
+ unsigned char crc;
+
+ /* Initialize delay factor based on loop time: 3*(uS-1) + 3 */
+ ds2411_delay_factor = MIN(cpu_frequency / (1000000*3), 1);
+
+ /* Init GPIO 1 wire bus for bit banging with a pullup resistor where
+ * it is set low as output and switched between input and output mode.
+ * Required for bidirectional communication on a single wire.
+ */
+ or_l(DS2411_BIT, &GPIO_FUNCTION); /* Set pin as GPIO */
+ and_l(~DS2411_BIT, &GPIO_ENABLE); /* Set as input */
+ and_l(~DS2411_BIT, &GPIO_OUT); /* Set low when set as output */
+
+ /* Delay 100us to stabilize */
+ DELAY(100);
+
+ /* Issue reset pulse - 480uS or more to ensure standard (not overdrive)
+ mode - we don't have the timing accuracy for that. */
+ or_l(DS2411_BIT, &GPIO_ENABLE);
+ /* Delay 560us: (Trstlmin + Trstlmax) / 2*/
+ DELAY(560);
+ and_l(~DS2411_BIT, &GPIO_ENABLE);
+ /* Delay 66us: Tpdhmax + 6 */
+ DELAY(66);
+
+ /* Read presence pulse - line should be pulled low at proper time by the
+ slave device */
+ if (GPIO_READ & DS2411_BIT)
+ {
+ logf("ds2411: no presence pulse");
+ return DS2411_NO_PRESENCE;
+ }
+
+ /* Trsth + 1 - 66 = Tpdhmax + Tpdlmax + Trecmin + 1 - 66 */
+ DELAY(240);
+
+ /* ds2411 should be ready for data transfer */
+
+ /* Send Read ROM command */
+ ds2411_write_byte(0x33);
+
+ /* Read ROM serial number and CRC */
+ i = 0, crc = 0;
+
+ do
+ {
+ unsigned char byte = ds2411_read_byte();
+ ((unsigned char *)id)[i] = byte;
+ crc = ds2411_calc_crc(crc ^ byte);
+ }
+ while (++i < 8);
+
+ /* Check that family code is ok */
+ if (id->family_code != 0x01)
+ {
+ logf("ds2411: invalid family code=%02X", (unsigned)id->family_code);
+ return DS2411_INVALID_FAMILY_CODE;
+ }
+
+ /* Check that CRC was ok */
+ if (crc != 0) /* Because last loop eors the CRC with the resulting CRC */
+ {
+ logf("ds2411: invalid CRC=%02X", (unsigned)id->crc);
+ return DS2411_INVALID_CRC;
+ }
+
+ /* Good ID read */
+ return DS2411_OK;
+} /* ds2411_read_id */