From d076ad3dbeac4bf7a58a335348c1560dd23799a7 Mon Sep 17 00:00:00 2001 From: Koen Kooi Date: Sat, 10 Jan 2009 10:44:13 +0100 Subject: gumstix utils: add char-driver, gpio-event, i2c and microwindows --- packages/char-driver/char-driver.bb | 62 ++ packages/char-driver/char-driver/makefile.patch | 26 + packages/char-driver/char-driver/sysctl.patch | 34 + packages/gpio-event/gpio-event.bb | 61 ++ packages/gpio-event/gpio-event/makefile.patch | 26 + packages/i2c/files/Config.h | 41 + packages/i2c/files/Crc8.c | 149 +++ packages/i2c/files/Crc8.h | 54 ++ packages/i2c/files/DumpMem.c | 93 ++ packages/i2c/files/DumpMem.h | 49 + packages/i2c/files/Log.c | 335 +++++++ packages/i2c/files/Log.h | 232 +++++ packages/i2c/files/i2c-api.c | 522 ++++++++++ packages/i2c/files/i2c-api.h | 143 +++ packages/i2c/files/i2c-dev.h | 365 +++++++ packages/i2c/files/i2c-io-api.h | 52 + packages/i2c/files/i2c-io.h | 220 +++++ packages/i2c/files/i2c.c | 710 ++++++++++++++ packages/i2c/files/i2c.h | 135 +++ packages/i2c/files/i2c.init | 37 + packages/i2c/i2c.bb | 45 + packages/microwindows/files/defconfig | 381 ++++++++ packages/microwindows/files/makefilerules.patch | 14 + packages/microwindows/files/nochown.patch | 17 + packages/microwindows/files/pagesize.patch | 10 + packages/microwindows/files/staticwin.patch | 11 + packages/microwindows/files/varargs.patch | 11 + packages/microwindows/microwindows-snapshot.bb | 10 + packages/microwindows/microwindows.inc | 55 ++ packages/microwindows/microwindows_0.90.bb | 45 +- packages/microwindows/microwindows_0.91.bb | 10 + packages/microwindows/nxlib_0.45.bb | 24 + packages/robostix-module/files/Makefile | 19 + packages/robostix-module/files/robostix.c | 1011 ++++++++++++++++++++ packages/robostix-module/files/robostix.h | 114 +++ packages/robostix-module/files/robostix.init | 53 + packages/robostix-module/robostix-module.bb | 36 + packages/robostix-utils/robostix-cmdline.bb | 28 + .../robostix-utils/robostix-cmdline/robostix.c | 278 ++++++ .../robostix-utils/robostix-cmdline/robostix.h | 114 +++ packages/robostix-utils/robostix-sertest.bb | 28 + packages/robostix-utils/robostix-sertest/sertest.c | 443 +++++++++ packages/robostix/robostix.bb | 135 +++ packages/robostix/robostix/gummake.patch | 26 + packages/robostix/robostix/makefile-rules.patch | 25 + 45 files changed, 6251 insertions(+), 38 deletions(-) create mode 100644 packages/char-driver/char-driver.bb create mode 100644 packages/char-driver/char-driver/makefile.patch create mode 100644 packages/char-driver/char-driver/sysctl.patch create mode 100644 packages/gpio-event/gpio-event.bb create mode 100644 packages/gpio-event/gpio-event/makefile.patch create mode 100644 packages/i2c/files/Config.h create mode 100644 packages/i2c/files/Crc8.c create mode 100644 packages/i2c/files/Crc8.h create mode 100644 packages/i2c/files/DumpMem.c create mode 100644 packages/i2c/files/DumpMem.h create mode 100644 packages/i2c/files/Log.c create mode 100644 packages/i2c/files/Log.h create mode 100644 packages/i2c/files/i2c-api.c create mode 100644 packages/i2c/files/i2c-api.h create mode 100644 packages/i2c/files/i2c-dev.h create mode 100644 packages/i2c/files/i2c-io-api.h create mode 100644 packages/i2c/files/i2c-io.h create mode 100644 packages/i2c/files/i2c.c create mode 100644 packages/i2c/files/i2c.h create mode 100755 packages/i2c/files/i2c.init create mode 100644 packages/i2c/i2c.bb create mode 100644 packages/microwindows/files/defconfig create mode 100644 packages/microwindows/files/makefilerules.patch create mode 100644 packages/microwindows/files/nochown.patch create mode 100644 packages/microwindows/files/pagesize.patch create mode 100644 packages/microwindows/files/staticwin.patch create mode 100644 packages/microwindows/files/varargs.patch create mode 100644 packages/microwindows/microwindows-snapshot.bb create mode 100644 packages/microwindows/microwindows.inc create mode 100644 packages/microwindows/microwindows_0.91.bb create mode 100644 packages/microwindows/nxlib_0.45.bb create mode 100644 packages/robostix-module/files/Makefile create mode 100644 packages/robostix-module/files/robostix.c create mode 100644 packages/robostix-module/files/robostix.h create mode 100755 packages/robostix-module/files/robostix.init create mode 100644 packages/robostix-module/robostix-module.bb create mode 100644 packages/robostix-utils/robostix-cmdline.bb create mode 100644 packages/robostix-utils/robostix-cmdline/robostix.c create mode 100644 packages/robostix-utils/robostix-cmdline/robostix.h create mode 100644 packages/robostix-utils/robostix-sertest.bb create mode 100644 packages/robostix-utils/robostix-sertest/sertest.c create mode 100644 packages/robostix/robostix.bb create mode 100644 packages/robostix/robostix/gummake.patch create mode 100644 packages/robostix/robostix/makefile-rules.patch diff --git a/packages/char-driver/char-driver.bb b/packages/char-driver/char-driver.bb new file mode 100644 index 0000000000..e6458b599b --- /dev/null +++ b/packages/char-driver/char-driver.bb @@ -0,0 +1,62 @@ +DESCRIPTION = "char-driver and userspace program" +PRIORITY = "optional" +SECTION = "base" +LICENSE = "GPL" +RDEPENDS = "kernel (${KERNEL_VERSION})" +DEPENDS = "virtual/kernel" + +PR = "r3" + +SRC_URI = "http://www.davehylands.com/gumstix-wiki/char-driver/char-driver-2.6.21.tar.gz \ + file://makefile.patch;patch=1 \ +# file://sysctl.patch;patch=1 \ + " + +S = "${WORKDIR}/char-driver" + +inherit module-base + +addtask builddir after do_fetch before do_unpack +addtask movesrc after do_unpack before do_patch + +EXTRA_OEMAKE = 'CROSS_COMPILE="${CROSS_COMPILE}" \ + KERNELDIR="${KERNEL_SOURCE}" \ + CC="${CC}" \ + ' + +PARALLEL_MAKE = "" + +do_builddir () { + mkdir -p ${S} +} + +do_movesrc () { + cd ${WORKDIR} + mv char-driver*.c sample.c char-driver*.h Makefile ${S} +} + +do_configure () { + echo "Nothing to configure for char-driver" +} + +do_compile () { + unset CFLAGS CPPFLAGS CXXFLAGS LDFLAGS + cd ${S} + oe_runmake +} + +do_install () { + # install programs to bindir + install -m 0755 -d ${D}${bindir} + install -m 0755 ${S}/sample ${D}${bindir} + + # kernel module installs with other modules + install -m 0755 -d ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + # use cp instead of install so the driver doesn't get stripped + cp ${S}/char-driver.ko ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ +} + +PACKAGES = "${PN}" +FILES_${PN} = "${bindir}/sample" +FILES_${PN} += "${base_libdir}/modules/${KERNEL_VERSION}/extra/char-driver.ko" + diff --git a/packages/char-driver/char-driver/makefile.patch b/packages/char-driver/char-driver/makefile.patch new file mode 100644 index 0000000000..d2d8e3c705 --- /dev/null +++ b/packages/char-driver/char-driver/makefile.patch @@ -0,0 +1,26 @@ +--- char-driver/Makefile.orig 2008-03-09 14:38:02.000000000 -0600 ++++ char-driver/Makefile 2008-03-09 14:39:04.000000000 -0600 +@@ -19,10 +19,10 @@ + + PWD := $(shell pwd) + +-GUMSTIX_BUILDROOT = $(PWD)/../gumstix-buildroot +-BUILD_ARM = $(wildcard $(GUMSTIX_BUILDROOT)/build_arm*) +-KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) +-CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- ++#GUMSTIX_BUILDROOT = $(PWD)/../gumstix-buildroot ++#BUILD_ARM = $(wildcard $(GUMSTIX_BUILDROOT)/build_arm*) ++#KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) ++#CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- + + default: user-apps kernel-module + +@@ -31,7 +31,7 @@ + user-apps: sample + + TARGET_ARCH=-Os -march=armv5te -mtune=xscale -Wa,-mcpu=xscale +-CC = $(CROSS_COMPILE)gcc ++#CC = $(CROSS_COMPILE)gcc + + sample: sample.c + diff --git a/packages/char-driver/char-driver/sysctl.patch b/packages/char-driver/char-driver/sysctl.patch new file mode 100644 index 0000000000..1c7a7600ba --- /dev/null +++ b/packages/char-driver/char-driver/sysctl.patch @@ -0,0 +1,34 @@ +--- char-driver/char-driver.c.orig 2008-03-09 13:05:30.000000000 -0600 ++++ char-driver/char-driver.c 2008-03-09 13:04:33.000000000 -0600 +@@ -26,7 +26,6 @@ + /* ---- Include Files ---------------------------------------------------- */ + + #include +-#include + #include + #include + #include +@@ -426,12 +425,17 @@ + printk( "sample driver allocated major:%d minor:%d\n", MAJOR( gSampleDevNum ), MINOR( gSampleDevNum )); + + // Register our proc entries. +- +- gSysCtlHeader = register_sysctl_table( gSysCtl, 0 ); +- if ( gSysCtlHeader != NULL ) +- { +- gSysCtlHeader->ctl_table->child->de->owner = THIS_MODULE; +- } ++#if USE_SYSCTL ++ #if ( LINUX_VERSION_CODE <= KERNEL_VERSION( 2, 6, 20 )) ++ gSysCtlHeader = register_sysctl_table( gSysCtl, 0 ); ++ if ( gSysCtlHeader != NULL ) ++ { ++ gSysCtlHeader->ctl_table->child->de->owner = THIS_MODULE; ++ } ++ #else ++ gSysCtlHeader = register_sysctl_table( gSysCtl ); ++ #endif ++#endif + + // Register our device. The device becomes "active" as soon as cdev_add + // is called. diff --git a/packages/gpio-event/gpio-event.bb b/packages/gpio-event/gpio-event.bb new file mode 100644 index 0000000000..afb2a77ac1 --- /dev/null +++ b/packages/gpio-event/gpio-event.bb @@ -0,0 +1,61 @@ +DESCRIPTION = "gpio-event driver and userspace program" +PRIORITY = "optional" +SECTION = "base" +LICENSE = "GPL" +RDEPENDS = "kernel (${KERNEL_VERSION})" +DEPENDS = "virtual/kernel" + +PR = "r4" + +SRC_URI = "http://davehylands.com/gumstix-wiki/gpio-event/gpio-event-2.6.21-1444-select.tar.gz \ + file://makefile.patch;patch=1 \ + " + +S = "${WORKDIR}/gpio-event" + +inherit module-base + +addtask builddir after do_fetch before do_unpack +addtask movesrc after do_unpack before do_patch + +EXTRA_OEMAKE = 'CROSS_COMPILE="${CROSS_COMPILE}" \ + KERNELDIR="${KERNEL_SOURCE}" \ + CC="${CC}" \ + ' + +PARALLEL_MAKE = "" + +do_builddir () { + mkdir -p ${S} +} + +do_movesrc () { + cd ${WORKDIR} + mv gpio-event*.c gpio-event*.h Makefile ${S} +} + +do_configure () { + echo "Nothing to configure for gpio-event" +} + +do_compile () { + unset CFLAGS CPPFLAGS CXXFLAGS LDFLAGS + cd ${S} + oe_runmake +} + +do_install () { + # install programs to bindir + install -m 0755 -d ${D}${bindir} + install -m 0755 ${S}/gpio-event ${D}${bindir} + + # kernel module installs with other modules + install -m 0755 -d ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + # use cp instead of install so the driver doesn't get stripped + cp ${S}/gpio-event-drv.ko ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ +} + +PACKAGES = "${PN}" +FILES_${PN} = "${bindir}/gpio-event" +FILES_${PN} += "${base_libdir}/modules/${KERNEL_VERSION}/extra/gpio-event-drv.ko" + diff --git a/packages/gpio-event/gpio-event/makefile.patch b/packages/gpio-event/gpio-event/makefile.patch new file mode 100644 index 0000000000..e1b7fe31b9 --- /dev/null +++ b/packages/gpio-event/gpio-event/makefile.patch @@ -0,0 +1,26 @@ +--- gpio-event/Makefile.orig 2008-03-09 13:59:07.000000000 -0600 ++++ gpio-event/Makefile 2008-03-09 13:59:51.000000000 -0600 +@@ -19,10 +19,10 @@ + + PWD := $(shell pwd) + +-GUMSTIX_BUILDROOT = $(PWD)/../cx-1575 +-BUILD_ARM = $(wildcard $(GUMSTIX_BUILDROOT)/build_arm*) +-KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) +-CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- ++#GUMSTIX_BUILDROOT = $(PWD)/../cx-1575 ++#BUILD_ARM = $(wildcard $(GUMSTIX_BUILDROOT)/build_arm*) ++#KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) ++#CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- + + default: user-apps kernel-module + +@@ -31,7 +31,7 @@ + user-apps: gpio-event + + TARGET_ARCH=-Os -march=armv5te -mtune=xscale -Wa,-mcpu=xscale +-CC = $(CROSS_COMPILE)gcc ++#CC = $(CROSS_COMPILE)gcc + + CPPFLAGS += + CFLAGS += -Wall diff --git a/packages/i2c/files/Config.h b/packages/i2c/files/Config.h new file mode 100644 index 0000000000..83bb46de84 --- /dev/null +++ b/packages/i2c/files/Config.h @@ -0,0 +1,41 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file Config.h +* +* @brief Global Configuration information. +* +****************************************************************************/ + +#if !defined( CONFIG_H ) +#define CONFIG_H /**< Include Guard */ + +/* ---- Include Files ---------------------------------------------------- */ + +/* ---- Constants and Types ---------------------------------------------- */ + +/** + * Sets Logging parameters + */ + +#define CFG_LOG_TO_BUFFER 0 + +#define CFG_CRC8BLOCK 1 + +/** @} */ + +#endif // CONFIG_H + diff --git a/packages/i2c/files/Crc8.c b/packages/i2c/files/Crc8.c new file mode 100644 index 0000000000..87dcf5c2f4 --- /dev/null +++ b/packages/i2c/files/Crc8.c @@ -0,0 +1,149 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file Crc8.c +* +* @brief This file contains the definition of the CRC-8 algorithim +* used by SMBus +* +* +*****************************************************************************/ + +/* ---- Include Files ----------------------------------------------------- */ + +#include "Config.h" + +#include "Crc8.h" + +#include "Log.h" + +/* ---- Public Variables -------------------------------------------------- */ +/* ---- Private Constants and Types --------------------------------------- */ +/* ---- Private Variables ------------------------------------------------- */ +/* ---- Private Function Prototypes --------------------------------------- */ +/* ---- Functions --------------------------------------------------------- */ + +/****************************************************************************/ +/** +* Calculates the CRC-8 used as part of SMBus. +* +* CRC-8 is defined to be x^8 + x^2 + x + 1 +* +* To use this function use the following template: +* +* crc = Crc8( crc, data ); +*/ + +#if 0 // Traditional implementation + +#define POLYNOMIAL (0x1070U << 3) + +unsigned char Crc8( unsigned char inCrc, unsigned char inData ) +{ + int i; + unsigned short data; + + data = inCrc ^ inData; + data <<= 8; + + for ( i = 0; i < 8; i++ ) + { + if (( data & 0x8000 ) != 0 ) + { + data = data ^ POLYNOMIAL; + } + data = data << 1; + } + +#if 0 +#if defined( LogBuf2 ) + LogBuf2( "Crc8: data:0x%02x crc:0x%02x\n", inData, (unsigned char)( data >> 8 )); +#else + + Log( "Crc8: data:0x%02x crc:0x%02x\n", inData, (unsigned char)( data >> 8 )); +#endif + +#endif + + + return (unsigned char)( data >> 8 ); + +} // Crc8 + +#else // Optimized for 8 bit CPUs (0x22 bytes on ATMega128 versus 0x30 for above version) + +unsigned char Crc8( unsigned char inCrc, unsigned char inData ) +{ + unsigned char i; + unsigned char data; + + data = inCrc ^ inData; + + for ( i = 0; i < 8; i++ ) + { + if (( data & 0x80 ) != 0 ) + { + data <<= 1; + data ^= 0x07; + } + else + { + data <<= 1; + } + } + +#if 0 +#if defined( LogBuf2 ) + LogBuf2( "Crc8: data:0x%02x crc:0x%02x\n", inData, data ); +#else + + Log( "Crc8: data:0x%02x crc:0x%02x\n", inData, data ); +#endif + +#endif + + + return data; + +} // Crc8 + +#endif + + +#if defined( CFG_CRC8BLOCK ) + +/****************************************************************************/ +/** +* Calculates the CRC-8 used as part of SMBus over a block of memory. +*/ + +uint8_t Crc8Block( uint8_t crc, uint8_t *data, uint8_t len ) +{ + while ( len > 0 ) + { + crc = Crc8( crc, *data++ ); + len--; + } + + return crc; + +} // Crc8Block + +#endif // CFG_CRC8BLOCK + +/** @} */ + + diff --git a/packages/i2c/files/Crc8.h b/packages/i2c/files/Crc8.h new file mode 100644 index 0000000000..2d1f74b82c --- /dev/null +++ b/packages/i2c/files/Crc8.h @@ -0,0 +1,54 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file Crc8.h +* +* @brief This file contains the definition of the CRC-8 algorithim +* used by SMBus +* +****************************************************************************/ + +#if !defined( CRC8_H ) +#define CRC_H ///< Include Guard + +/* ---- Include Files ----------------------------------------------------- */ + +#include + +#if defined( __cplusplus ) +extern "C" +{ +#endif + + +/* ---- Constants and Types ---------------------------------------------- */ +/* ---- Variable Externs ------------------------------------------------- */ +/* ---- Function Prototypes ---------------------------------------------- */ + +uint8_t Crc8( uint8_t crc, uint8_t data ); + +uint8_t Crc8Block( uint8_t crc, uint8_t *data, uint8_t len ); + + +#if defined( __cplusplus ) +} +#endif + + +/** @} */ + +#endif // CRC8_H + diff --git a/packages/i2c/files/DumpMem.c b/packages/i2c/files/DumpMem.c new file mode 100644 index 0000000000..e13e94b0f8 --- /dev/null +++ b/packages/i2c/files/DumpMem.c @@ -0,0 +1,93 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file DumpMem.c +* +* @brief Memmory dump routine +* +****************************************************************************/ + +// ---- Include Files ------------------------------------------------------- + +#include +#include "DumpMem.h" +#include "Log.h" + +// ---- Public Variables ---------------------------------------------------- +// ---- Private Constants and Types ----------------------------------------- +// ---- Private Variables --------------------------------------------------- +// ---- Private Function Prototypes ----------------------------------------- +// ---- Functions ----------------------------------------------------------- + +/**************************************************************************/ +/** +* Dumps a page of output for debugging purposes. +*/ + +void DumpMem( const char *prefix, unsigned address, const void *inData, unsigned numBytes ) +{ + const uint8_t *data = (const uint8_t *)inData; + unsigned byteOffset; + + if ( numBytes == 0 ) + { + Log( "%s: No data\n", prefix ); + return; + } + +#define LINE_WIDTH 16 + + for ( byteOffset = 0; byteOffset < numBytes; byteOffset += LINE_WIDTH ) + { + unsigned i; + + Log( "%s: %04x: ", prefix, address + byteOffset ); + + for ( i = 0; i < LINE_WIDTH; i++ ) + { + if (( byteOffset + i ) < numBytes ) + { + Log( "%02.2X ", data[ byteOffset + i ] ); + } + else + { + Log( " " ); + } + } + for ( i = 0; i < LINE_WIDTH; i++ ) + { + if (( byteOffset + i ) < numBytes ) + { + unsigned char ch = data[ byteOffset + i ]; + if (( ch < ' ' ) || ( ch > '~' )) + { + Log( "." ); + } + else + { + Log( "%c", ch ); + } + } + else + { + break; + } + } + Log( "\n" ); + } + +} // DumpMem + diff --git a/packages/i2c/files/DumpMem.h b/packages/i2c/files/DumpMem.h new file mode 100644 index 0000000000..5d536f49e8 --- /dev/null +++ b/packages/i2c/files/DumpMem.h @@ -0,0 +1,49 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file DumpMem.h +* +* @brief Debug routine for dumping memory +* +****************************************************************************/ + +#if !defined( DUMPMEM_H ) +#define DUMPMEM_H ///< Include Guard + +// ---- Include Files ------------------------------------------------------- + +/** + * @addtogroup Log + * @{ + */ + +#if defined( __cplusplus ) +extern "C" +{ +#endif + + +void DumpMem( const char *prefix, unsigned address, const void *data, unsigned numBytes ); + +#if defined( __cplusplus ) +} +#endif + + +/** @} */ + +#endif // DUMPMEM_H + diff --git a/packages/i2c/files/Log.c b/packages/i2c/files/Log.c new file mode 100644 index 0000000000..e32783391b --- /dev/null +++ b/packages/i2c/files/Log.c @@ -0,0 +1,335 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file Log.cpp +* +* @brief This file contains the implementation of the logging functions. +* +****************************************************************************/ + +// ---- Include Files ------------------------------------------------------- + +#include "Log.h" + +#if CFG_LOG_USE_STDIO +# include +#else + +# include "Str.h" +# include "UART.h" +#endif + + +// ---- Public Variables ---------------------------------------------------- +// ---- Private Constants and Types ----------------------------------------- + +#if defined( AVR ) + +#undef Log +#undef LogError +#undef vLog + +#define Log Log_P +#define LogError LogError_P +#define vLog vLog_P +#define LogBuf LogBuf_P + +#define char prog_char + +#else + + +#define PSTR(str) str + +int gVerbose = 0; +int gDebug = 0; +int gQuiet = 0; + +#endif + + +#if CFG_LOG_TO_BUFFER + +volatile LOG_Buffer_t LOG_gBuffer; + +#endif + + +// ---- Private Variables --------------------------------------------------- + +#if CFG_LOG_USE_STDIO + +FILE *gLogFs = NULL; + +#endif + + +// ---- Private Function Prototypes ----------------------------------------- + +// ---- Functions ----------------------------------------------------------- + +/** + * @addtogroup Log + * @{ + */ + +#if !defined( AVR ) + +void DefaultLogFunc( int logLevel, const char *fmt, va_list args ) +{ + FILE *fs; + + if ( gQuiet && ( logLevel == LOG_LEVEL_NORMAL )) + { + return; + } + + if ( gLogFs == NULL ) + { + fs = stderr; + } + else + { + fs = gLogFs; + } + + if ( logLevel == LOG_LEVEL_ERROR ) + { + fprintf( fs, "ERROR: " ); + } + vfprintf( fs, fmt, args ); + fflush( fs ); + +} // DefaultLogFunc + +static LogFunc_t gLogFunc = DefaultLogFunc; + +void SetLogFunc( LogFunc_t logFunc ) +{ + + gLogFunc = logFunc; + +} // SetLogFunc + +#endif + + +//*************************************************************************** +/** +* Sets the logging stream +*/ + +#if CFG_LOG_USE_STDIO +void LogInit( FILE *logFs ) +{ + gLogFs = logFs; + +} // LogInit + +#else + + +static int LogToUartFunc( void *outParm, int ch ) +{ + UART0_PutChar( ch ); + + return 1; +} +#endif + + +//*************************************************************************** +/** +* Logs a string using printf like semantics +*/ + +void Log +( + const char *fmt, ///< printf style format specifier + ... ///< variable list of arguments +) +{ + va_list args; + + va_start( args, fmt ); + vLog( fmt, args ); + va_end( args ); +} + +//*************************************************************************** +/** +* Logs a string using printf like semantics +*/ + +void vLog +( + const char *fmt, ///< printf style format specified + va_list args ///< variable list of arguments +) +{ + // For now we call printf directly. A better way would be to install + // a callback which does the real work + +#if defined( AVR ) +# if CFG_LOG_USE_STDIO + if ( gLogFs != NULL ) + { + vfprintf_P( gLogFs, fmt, args ); + } +# else + + vStrXPrintf_P( LogToUartFunc, NULL, fmt, args ); +# endif + +#else + + if ( gLogFunc != NULL ) + { + gLogFunc( LOG_LEVEL_NORMAL, fmt, args ); + } +#endif + +} + +#if !defined( AVR ) + +//*************************************************************************** +/** +* Logs an error. +*/ + +void vLogError +( + const char *fmt, ///< printf style format specified + va_list args ///< variable list of arguments +) +{ + if ( gLogFunc != NULL ) + { + gLogFunc( LOG_LEVEL_ERROR, fmt, args ); + } +} + +#endif + + +/***************************************************************************/ +/** +* Logs an error +*/ + +void LogError +( + const char *fmt, ///< printf style format specifier + ... ///< variable list of arguments +) +{ + va_list args; + +#if defined( AVR ) + //Log( "ERROR: " ); + //Log_P( PSTR( "ERROR: " )); + + va_start( args, fmt ); + vLog( fmt, args ); + va_end( args ); +#else + + va_start( args, fmt ); + vLogError( fmt, args ); + va_end( args ); +#endif + + +} // LogError + +/***************************************************************************/ +/** +* Logs an entry to the log buffer +*/ + +#if CFG_LOG_TO_BUFFER + +void LogBuf( const char *fmt, uint8_t arg1, uint8_t arg2 LOG_EXTRA_PARAMS_DECL ) +{ +#if defined( AVR ) + uint8_t sreg = SREG; + cli(); +#endif + + + if ( CBUF_IsFull( LOG_gBuffer )) + { + volatile LOG_Entry_t *entry = CBUF_GetLastEntryPtr( LOG_gBuffer ); + + entry->fmt = PSTR( "*** Lost Messages ***\n" ); + } + else + { + volatile LOG_Entry_t *entry = CBUF_GetPushEntryPtr( LOG_gBuffer ); + + entry->fmt = fmt; + entry->param1 = arg1; + entry->param2 = arg2; + +#if CFG_LOG_EXTRA_PARAMS + entry->param3 = arg3; + entry->param4 = arg4; +#endif + + + CBUF_AdvancePushIdx( LOG_gBuffer ); + } + +#if defined( AVR ) + SREG = sreg; +#endif + + +} // LogBuf + +#endif // CFG_LOG_TO_BUFFER + +/***************************************************************************/ +/** +* Dumps any unlogged entries from the log buffer +*/ + +#if CFG_LOG_TO_BUFFER + +void LogBufDump( void ) +{ + while ( !CBUF_IsEmpty( LOG_gBuffer )) + { + volatile LOG_Entry_t *entry = CBUF_GetPopEntryPtr( LOG_gBuffer ); + +#if CFG_LOG_EXTRA_PARAMS + Log( entry->fmt, entry->param1, entry->param2, entry->param3, entry->param4 ); +#else + + Log( entry->fmt, entry->param1, entry->param2 ); +#endif + + + CBUF_AdvancePopIdx( LOG_gBuffer ); + } + +} // LogBufDump + +#endif // CFG_LOG_TO_BUFFER + +/** @} */ + diff --git a/packages/i2c/files/Log.h b/packages/i2c/files/Log.h new file mode 100644 index 0000000000..d12d482fc6 --- /dev/null +++ b/packages/i2c/files/Log.h @@ -0,0 +1,232 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file Log.h +* +* @brief Contains some logging macros. +* +****************************************************************************/ +/** +* @defgroup Log Logging +* +* @brief Provides a common interface for logging. +* +****************************************************************************/ + +#if !defined( LOG_H ) +#define LOG_H ///< Include Guard + +// ---- Include Files ------------------------------------------------------- + +#include +#include + +#if !defined( CONFIG_H ) +# include "Config.h" +#endif + +#if !defined( CFG_LOG_USE_STDIO ) +# define CFG_LOG_USE_STDIO 1 +#endif + + +#if defined( AVR ) +# include +# include +#endif + + +#if CFG_LOG_TO_BUFFER +# if !defined( CBUF_H ) +# include "CBUF.h" +# endif + +#endif + + + +/** + * @addtogroup Log + * @{ + */ + +#if !defined( CFG_LOG_ENABLED ) +# define CFG_LOG_ENABLED 1 +#endif + + +#if !CFG_LOG_ENABLED + +#define Log( fmt, args... ) +#define LogError( fmt, args... ) + +#else + + +#if defined( __cplusplus ) +extern "C" +{ +#endif + + +/*************************************************************************** +* +* Log Buffer support +*/ + +#if CFG_LOG_TO_BUFFER + +#if defined( AVR ) + +typedef struct +{ + const prog_char *fmt; + uint8_t param1; + uint8_t param2; +#if CFG_LOG_EXTRA_PARAMS + uint8_t param3; + uint8_t param4; +#endif + + +} LOG_Entry_t; + +#if CFG_LOG_EXTRA_PARAMS +# define LOG_EXTRA_PARAMS_DECL , uint8_t arg3, uint8_t arg4 +# define LOG_EXTRA_PARAMS , 0, 0 +#else + +# define LOG_EXTRA_PARAMS_DECL +# define LOG_EXTRA_PARAMS +#endif + + +void LogBuf_P( const prog_char *fmt, uint8_t arg1, uint8_t arg2 LOG_EXTRA_PARAMS_DECL ); + +#define LogBuf0( fmt ) LogBuf_P( PSTR( fmt ), 0, 0 LOG_EXTRA_PARAMS ) +#define LogBuf1( fmt, arg1 ) LogBuf_P( PSTR( fmt ), arg1, 0 LOG_EXTRA_PARAMS ) +#define LogBuf2( fmt, arg1, arg2 ) LogBuf_P( PSTR( fmt ), arg1, arg2 LOG_EXTRA_PARAMS ) + +#if CFG_LOG_EXTRA_PARAMS +#define LogBuf3( fmt, arg1, arg2, arg3 ) LogBuf_P( PSTR( fmt ), arg1, arg2, arg3, 0 ) +#define LogBuf4( fmt, arg1, arg2, arg3, arg4 ) LogBuf_P( PSTR( fmt ), arg1, arg2, arg3, arg4 ) +#endif + + +#else + + +typedef struct +{ + const char *fmt; + uint8_t param1; + uint8_t param2; + +} LOG_Entry_t; + +void LogBuf( const char *fmt, uint8_t arg1, uint8_t arg2 ); + +#define LogBuf0( fmt, arg1 ) LogBuf( fmt, 0, 0 ) +#define LogBuf1( fmt, arg1 ) LogBuf( fmt, arg1, 0 ) +#define LogBuf2( fmt, arg1, arg2 ) LogBuf( fmt, arg1, arg2 ) + +#endif // AVR + +#if ( CFG_LOG_NUM_BUFFER_ENTRIES > 128 ) +typedef uint16_t LOG_BufferIdx_t; +#else + +typedef uint8_t LOG_BufferIdx_t; +#endif + + +typedef struct +{ + LOG_BufferIdx_t m_getIdx; + LOG_BufferIdx_t m_putIdx; + LOG_Entry_t m_entry[ CFG_LOG_NUM_BUFFER_ENTRIES ]; + +} LOG_Buffer_t; + +extern volatile LOG_Buffer_t LOG_gBuffer; + +#define LOG_gBuffer_SIZE ( sizeof( LOG_gBuffer.m_entry ) / sizeof( LOG_gBuffer.m_entry[ 0 ] )) + +void LogBufDump( void ); + +#endif // CFG_LOG_TO_BUFFER + +/*************************************************************************** +* +* Regular logging support +*/ + +#if CFG_LOG_USE_STDIO +extern FILE *gLogFs; + +void LogInit( FILE *logFs ); +#endif + + +#if defined( AVR ) + +void Log_P( const prog_char *fmt, ... ); +void LogError_P( const prog_char *fmt, ... ); +void vLog_P( const prog_char *fmt, va_list args ); + +#define Log( fmt, args... ) Log_P( PSTR( fmt ), ## args ) +#define LogError( fmt, args... ) LogError_P( PSTR( fmt ), ## args ) +#define vLog( fmt, va_list, args ) vLog_P( PSTR( fmt ), args ) + +#else // AVR + +#define LOG_LEVEL_NORMAL 0 +#define LOG_LEVEL_ERROR 1 + +typedef void (*LogFunc_t)( int logLevel, const char *fmt, va_list args ); + +extern int gVerbose; +extern int gDebug; +extern int gQuiet; + +void Log( const char *fmt, ... ); +void LogError( const char *fmt, ... ); +void vLog( const char *fmt, va_list args ); +void vLogError( const char *fmt, va_list args ); + +#define Log_P( fmt, args... ) Log( fmt, ## args ) +#define LogError_P( fmt, args... ) LogError( fmt, ## args ) +#define vLog_P( fmt, args ) vLog( fmt, args ) + +#define LogDebug( fmt, args... ) do { if ( gDebug ) { Log( fmt, ## args ); }} while (0) +#define LogVerbose( fmt, args... ) do { if ( gVerbose ) { Log( fmt, ## args ); }} while (0) + +void SetLogFunc( LogFunc_t logFunc ); +void DefaultLogFunc( int logLevel, const char *fmt, va_list args ); + +#endif // AVR + +#if defined( __cplusplus ) +} +#endif + + +#endif // CFG_LOG_ENABLED + +/** @} */ + +#endif // LOG_H + diff --git a/packages/i2c/files/i2c-api.c b/packages/i2c/files/i2c-api.c new file mode 100644 index 0000000000..cfc41565a4 --- /dev/null +++ b/packages/i2c/files/i2c-api.c @@ -0,0 +1,522 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c-api.c +* +* @brief This file contains the implementation for performing I2C operations +* on the gumstix. +* +****************************************************************************/ + +// ---- Include Files ------------------------------------------------------- + +#include +#include + +#include "i2c.h" +#include "i2c-dev.h" +#include "i2c-api.h" + +#include "Crc8.h" +#include "DumpMem.h" +#include "Log.h" + +// ---- Public Variables ---------------------------------------------------- + +// ---- Private Constants and Types ----------------------------------------- + +// ---- Private Variables --------------------------------------------------- + +static I2C_Addr_t gI2cAddr; +static int gUseCrc; + +// ---- Private Function Prototypes ----------------------------------------- + +// ---- Functions ----------------------------------------------------------- + +//*************************************************************************** +/** +* +* Sets the I2C address that we'll be communicating with, as well as whether +* the device uses smbus PEC (CRC). +*/ + +void I2cSetSlaveAddress( int i2cDev, I2C_Addr_t i2cAddr, int useCrc ) +{ + gI2cAddr = i2cAddr; + gUseCrc = useCrc; + + LogDebug( "----- I2cSetSlaveAddress i2cAddr:0x%02x useCrc:%d -----\n", + i2cAddr, useCrc ); + + // Indicate which slave we wish to speak to + + if ( ioctl( i2cDev, I2C_SLAVE, gI2cAddr ) < 0 ) + { + LogError( "I2cSetSlaveAddress: Error trying to set slave address to 0x%02x (%d %s)\n", + gI2cAddr, errno, strerror( errno )); + } + + // We do the CRC calculation ourself, so we don't need to tell the driver + // that we're using it. + +#if 0 + // Indicate that we use PEC (aka CRCs) + + if ( ioctl( i2cDev, I2C_PEC, 1 ) < 0 ) + { + LogError( "I2cSetSlaveAddress: Error trying to set PEC mode\n" ); + } +#endif + +} // I2cSetSlaveAddress + +//*************************************************************************** +/** +* Transfer data to/from an i2c device. +* +* This function implements the equivalent of the smbus functions using +* I2C_RDWR. +* +* The PXA driver doesn't support the smbus transfers. +* +* This function can perform the following SMBUS transactions: +* +* Write Byte: wrLen == 1, rdLen == 0 +* Read Byte: wrLen == 0, rdLen == 1 +* Write Word: wrLen == 2, rdLen == 0 +* Read Word: wrLen == 0, rdLen == 2 +* Process Call: wrLen == 2, rdLen == 2 +* Write Block: wrLen == 0x80 + numBytes, rdLen == 0 +* Read Block: wrLen == 0, rdLen == 0x80 + numBytes +* Process Block: wrLen == 0x80 + numBytes, rdLen == 0x80 + numBytes +*/ + +int I2cTransfer +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen, ///< Number of bytes to write (or in 0x80 for a block write) + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read (or in 0x80 for a block read) + uint8_t *bytesReadp ///< Place to store number of bytes read +) +{ + struct i2c_rdwr_ioctl_data rdwr; + struct i2c_msg msg[ 2 ]; + uint8_t wrBuf[ I2C_MAX_DATA_LEN + 3 ]; // +1 for cmd, +1 for len, +1 for CRC + uint8_t rdBuf[ I2C_MAX_DATA_LEN + 2 ]; // +1 for len, +1 for CRC + uint8_t crc = 0; + uint8_t wrBlock = (( wrLen & 0x80 ) != 0 ); + uint8_t rdBlock = (( rdLen & 0x80 ) != 0 ); + int rc = 0; + + LogDebug( "----- I2cTransfer: cmd:0x%02x wrLen:0x%02x rdLen:0x%02x wrBlock:%d rdBlock:%d -----\n", + cmd, wrLen, rdLen, wrBlock, rdBlock ); + if ( wrData != NULL ) + { + LogDebug( "----- wrData:0x%08x *wrData:0x%02x -----\n", wrData, *(const uint8_t *)wrData ); + } + + rdLen &= 0x7f; + wrLen &= 0x7f; + + if ( bytesReadp != NULL ) + { + *bytesReadp = 0; + } + + if ( wrLen > I2C_MAX_DATA_LEN ) + { + LogError( "I2cTransfer: wrLen too big: %d, max is %d\n", + wrLen, I2C_MAX_DATA_LEN ); + errno = ENOBUFS; + return -1; + } + + if ( rdLen > I2C_MAX_DATA_LEN ) + { + LogError( "I2cTransfer: rdLen too big: %d, max is %d\n", + rdLen, I2C_MAX_DATA_LEN ); + errno = ENOBUFS; + return -1; + } + + // Whether we're doing a read or a write, we always send + // the command. + + msg[ 0 ].addr = gI2cAddr; + msg[ 0 ].flags = 0; + msg[ 0 ].len = wrLen + 1 + wrBlock; // +1 for cmd + msg[ 0 ].buf = (char *)&wrBuf[ 0 ]; + + if ( gUseCrc ) + { + crc = Crc8( 0, gI2cAddr << 1 ); + crc = Crc8( crc, cmd ); + } + + wrBuf[ 0 ] = cmd; + + if ( wrLen > 0 ) + { + // We have some data to send down to the device + + if ( wrBlock ) + { + wrBuf[ 1 ] = wrLen; + memcpy( &wrBuf[ 2 ], wrData, wrLen ); + wrLen++; // Add in cmd to the length + } + else + { + memcpy( &wrBuf[ 1 ], wrData, wrLen ); + } + if ( gUseCrc ) + { + crc = Crc8Block( crc, &wrBuf[ 1 ], wrLen ); + + if ( rdLen == 0 ) + { + // This is a write-only, so we need to send the CRC + + wrBuf[ wrLen + 1 ] = crc; + msg[ 0 ].len++; + } + } + } + + if ( gDebug ) + { + Log( "msg[ 0 ].addr = 0x%02x\n", msg[ 0 ].addr ); + Log( "msg[ 0 ].flags = 0x%04x\n", msg[ 0 ].flags ); + Log( "msg[ 0 ].len = %d\n", msg[ 0 ].len ); + DumpMem( "I2cTransfer W", 0, &wrBuf[ 0 ], msg[ 0 ].len ); + } + + rdwr.msgs = msg; + rdwr.nmsgs = 1; + + if ( rdLen > 0 ) + { + // We're expecting some data to come back + + msg[ 1 ].addr = gI2cAddr; + msg[ 1 ].flags = I2C_M_RD; + msg[ 1 ].len = rdLen + rdBlock + gUseCrc; + msg[ 1 ].buf = (char *)&rdBuf[ 0 ]; + + rdwr.nmsgs = 2; + + if ( gUseCrc ) + { + crc = Crc8( crc, ( gI2cAddr << 1 ) | 1 ); + } + + if ( gDebug ) + { + Log( "msg[ 1 ].addr = 0x%02x\n", msg[ 1 ].addr ); + Log( "msg[ 1 ].flags = 0x%04x\n", msg[ 1 ].flags ); + Log( "msg[ 1 ].len = %d\n", msg[ 1 ].len ); + } + } + + if ( ioctl( i2cDev, I2C_RDWR, &rdwr ) < 0 ) + { + LogError( "I2cTransfer: ioctl failed: %s (%d)\n", strerror( errno ), errno ); + return -1; + } + + if ( rdLen > 0 ) + { + if ( rdBlock ) + { + if ( rdBuf[ 0 ] > rdLen ) + { + LogError( "I2cTransfer: length is too big: %d max: %d\n", rdBuf[ 0 ], rdLen ); + + rc = EMSGSIZE; + } + else + { + rdLen = rdBuf[ 0 ]; + } + } + + if ( gUseCrc ) + { + crc = Crc8Block( crc, &rdBuf[ 0 ], rdLen + rdBlock ); + + if ( crc != rdBuf[ rdLen + rdBlock ] ) + { + LogError( "I2cTransfer: CRC failed: Rcvd: 0x%02x, expecting: 0x%02x\n", + rdBuf[ rdLen + rdBlock ], crc ); + rc = EBADMSG; + } + } + + if ( gDebug ) + { + DumpMem( "I2cTransfer R", 0, &rdBuf[ 0 ], msg[ 1 ].len ); + } + memcpy( rdData, &rdBuf[ rdBlock ], rdLen ); + + if ( bytesReadp != NULL ) + { + *bytesReadp = rdLen; + } + } + return rc; + +} // I2cTransfer + +//*************************************************************************** +/** +* Uses the SMBUS Process-Block protocol to read data from a device. +*/ + +int I2cProcessBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen, ///< Number of bytes to write + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read + uint8_t *bytesReadp ///< Place to store number of bytes read +) +{ + LogDebug( "----- I2cProcessBlock cmd: 0x%02x wrLen:0x%02x rdLen:0x%02x -----\n", cmd, wrLen, rdLen ); + + return I2cTransfer( i2cDev, cmd, wrData, 0x80 | wrLen, rdData, 0x80 | rdLen, bytesReadp ); + +} // I2cProcessBlock + +//*************************************************************************** +/** +* Uses the SMBUS Read-Block protocol to read data from a device. +*/ + +int I2cReadBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read + uint8_t *bytesReadp ///< Place to store number of bytes read +) +{ + LogDebug( "----- I2cReadBlock cmd: 0x%02x rdLen:0x%02x -----\n", cmd, rdLen ); + + return I2cTransfer( i2cDev, cmd, NULL, 0, rdData, 0x80 | rdLen, bytesReadp ); + +} // I2cReadBlock + +//*************************************************************************** +/** +* Uses the SMBUS Read-Byte protocol to read a byte. +*/ + +int I2cReadByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + uint8_t *rdByte ///< Place to store byte read +) +{ + LogDebug( "----- I2cReadByte cmd: 0x%02x -----\n", cmd ); + + return I2cTransfer( i2cDev, cmd, NULL, 0, rdByte, 1, NULL ); + +} // I2cReadByte + +//*************************************************************************** +/** +* Reads an array of bytes usinng i2c (not compatible with SMBUS) +*/ + +int I2cReadBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + void *rdByte, ///< Place to store bytes read + uint8_t rdLen ///< Number of bytes to read +) +{ + LogDebug( "----- I2cReadBytes cmd: 0x%02x rdLen: 0x%02x -----\n", cmd, rdLen ); + + return I2cTransfer( i2cDev, cmd, NULL, 0, rdByte, rdLen, NULL ); + +} // I2cReadBytes + +//*************************************************************************** +/** +* Uses the SMBUS Write-Block protocol to write data from a device. +*/ + +int I2cWriteBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen ///< Number of bytes to write +) +{ + LogDebug( "----- I2cWriteBlock cmd: 0x%02x wrLen:0x%02x -----\n", cmd, wrLen ); + + return I2cTransfer( i2cDev, cmd, wrData, 0x80 | wrLen, NULL, 0, NULL ); + +} // I2cWriteBlock + +//*************************************************************************** +/** +* Uses the SMBUS Write-Byte protocol to write a byte. +*/ + +int I2cWriteByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + uint8_t wrByte ///< Byte to write +) +{ + LogDebug( "----- I2cWriteByte cmd: 0x%02x wrByte:0x%02x -----\n", cmd, wrByte ); + LogDebug( "----- &wrByte = 0x%08x wrByte = 0x%02x -----\n", &wrByte, *&wrByte ); + + return I2cTransfer( i2cDev, cmd, &wrByte, 1, NULL, 0, NULL ); + +} // I2cWriteByte + +//*************************************************************************** +/** +* Writes an array of bytes using i2c (not compatible with SMBUS) +*/ + +int I2cWriteBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrByte, ///< Bytes to write + uint8_t wrLen ///< Number of bytes to write +) +{ + LogDebug( "----- I2cWriteBytes cmd: 0x%02x wrLen: 0x%02x -----\n", cmd, wrLen ); + + return I2cTransfer( i2cDev, cmd, wrByte, wrLen, NULL, 0, NULL ); + +} // I2cWriteBytes + +//*************************************************************************** +/** +* Uses the SMBUS Receive-Byte protocol to read a byte. +*/ + +int I2cReceiveByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *rdByte ///< Place to store byte read +) +{ + return I2cReceiveBytes( i2cDev, rdByte, 1 ); + +} // I2cReceiveByte + +//*************************************************************************** +/** +* Uses the SMBUS Receive-Byte protocol to read multiple (or one or zero) bytes. +*/ + +int I2cReceiveBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *rdData, ///< Place to store data read + uint8_t rdLen ///< Number of bytes to read +) +{ + struct i2c_rdwr_ioctl_data rdwr; + struct i2c_msg msg; + + LogDebug( "----- I2cReceiveBytes -----\n" ); + + msg.addr = gI2cAddr; + msg.flags = I2C_M_RD; + msg.len = rdLen; + msg.buf = (char *)rdData; + + rdwr.msgs = &msg; + rdwr.nmsgs = 1; + + if ( ioctl( i2cDev, I2C_RDWR, &rdwr ) < 0 ) + { + LogError( "I2cReceiveBytes: ioctl failed: %s (%d)\n", strerror( errno ), errno ); + return -1; + } + + return 0; + +} // I2cReceiveBytes + +//*************************************************************************** +/** +* Uses the SMBUS Send-Byte protocol to write a byte. +*/ + +int I2cSendByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t wrByte ///< Byte to write +) +{ + return I2cSendBytes( i2cDev, &wrByte, 1 ); + +} // I2cSendByte + +//*************************************************************************** +/** +* Uses the SMBUS Send-Byte protocol to write multiple (or zero or one) bytes. +*/ + +int I2cSendBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *wrData, ///< Pointer to data to write + uint8_t wrLen ///< NUmber of bytes to write +) +{ + struct i2c_rdwr_ioctl_data rdwr; + struct i2c_msg msg; + + LogDebug( "----- I2cSendBytes wrLen = 0x%02x -----\n", wrLen ); + + msg.addr = gI2cAddr; + msg.flags = 0; + msg.len = wrLen; + msg.buf = (char *)wrData; + + rdwr.msgs = &msg; + rdwr.nmsgs = 1; + + if ( ioctl( i2cDev, I2C_RDWR, &rdwr ) < 0 ) + { + LogError( "I2cSendBytes: ioctl failed: %s (%d)\n", strerror( errno ), errno ); + return -1; + } + + return 0; + +} // I2cSendBytes + diff --git a/packages/i2c/files/i2c-api.h b/packages/i2c/files/i2c-api.h new file mode 100644 index 0000000000..73f9f20990 --- /dev/null +++ b/packages/i2c/files/i2c-api.h @@ -0,0 +1,143 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c-api.h +* +* @brief This file contains definitions for performing i2c operations +* on the gumstix. +* +****************************************************************************/ + +#if !defined( I2C_API_H ) +#define I2C_API_H + +// ---- Include Files ------------------------------------------------------- + +#include +#include "i2c.h" + +// ---- Constants and Types ------------------------------------------------- + +#define I2C_USE_CRC 1 +#define I2C_NO_CRC 0 + +// ---- Variable Externs ---------------------------------------------------- + +// ---- Function Prototypes ------------------------------------------------- + +void I2cSetSlaveAddress +( + int i2cDev, ///< Handle to i2c-dev file + I2C_Addr_t i2cAddr, ///< 7 bit i2c address to use + int useCrc ); ///< Should CRC's be used? + +int I2cTransfer +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen, ///< Number of bytes to write (or in 0x80 for a block write) + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read (or in 0x80 for a block read) + uint8_t *bytesReadp ///< Place to store number of bytes read +); + +int I2cProcessBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen, ///< Number of bytes to write + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read + uint8_t *bytesReadp ///< Place to store number of bytes read +); + +int I2cReadBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + void *rdData, ///< Place to store data read + uint8_t rdLen, ///< Number of bytes to read + uint8_t *bytesReadp ///< Place to store number of bytes read +); + +int I2cReadByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + uint8_t *rdByte ///< Place to store byte to read +); + +int I2cReadBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + void *rdByte, ///< Place to store bytes read + uint8_t rdLen ///< Number of bytes to read +); + +int I2cWriteBlock +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrData, ///< Data to write + uint8_t wrLen ///< Number of bytes to write +); + +int I2cWriteByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + uint8_t wrByte ///< Byte to write +); + +int I2cWriteBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t cmd, ///< Command to send + const void *wrByte, ///< Bytes to write + uint8_t wrLen ///< Number of bytes to write +); + +int I2cReceiveByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *rdByte ///< Place to store byte read +); + +int I2cReceiveBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *rdData, ///< Place to store byte read + uint8_t rdLen ///< Number of bytes to read +); + +int I2cSendByte +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t wrByte ///< Byte to write +); + +int I2cSendBytes +( + int i2cDev, ///< Handle to i2c-dev file + uint8_t *wrData, ///< Pointer to data to write. + uint8_t wrLen ///< Number of bytes to write. +); + +#endif // I2C_API_H + diff --git a/packages/i2c/files/i2c-dev.h b/packages/i2c/files/i2c-dev.h new file mode 100644 index 0000000000..cd20965ede --- /dev/null +++ b/packages/i2c/files/i2c-dev.h @@ -0,0 +1,365 @@ +/* + i2c-dev.h - i2c-bus driver, char device interface + + Copyright (C) 1995-97 Simon G. Vogl + Copyright (C) 1998-99 Frodo Looijaard + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +/* $Id: i2c-dev.h,v 1.4 2003/11/27 23:08:06 tat Exp $ */ + +#ifndef LIB_I2CDEV_H +#define LIB_I2CDEV_H + +#include +#include + + +/* -- i2c.h -- */ + + +/* + * I2C Message - used for pure i2c transaction, also from /dev interface + */ +struct i2c_msg { + __u16 addr; /* slave address */ + unsigned short flags; +#define I2C_M_TEN 0x10 /* we have a ten bit chip address */ +#define I2C_M_RD 0x01 +#define I2C_M_NOSTART 0x4000 +#define I2C_M_REV_DIR_ADDR 0x2000 +#define I2C_M_IGNORE_NAK 0x1000 +#define I2C_M_NO_RD_ACK 0x0800 + short len; /* msg length */ + char *buf; /* pointer to msg data */ +}; + +/* To determine what functionality is present */ + +#define I2C_FUNC_I2C 0x00000001 +#define I2C_FUNC_10BIT_ADDR 0x00000002 +#define I2C_FUNC_PROTOCOL_MANGLING 0x00000004 /* I2C_M_{REV_DIR_ADDR,NOSTART,..} */ +#define I2C_FUNC_SMBUS_HWPEC_CALC 0x00000008 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_READ_WORD_DATA_PEC 0x00000800 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_WRITE_WORD_DATA_PEC 0x00001000 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_PROC_CALL_PEC 0x00002000 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_BLOCK_PROC_CALL_PEC 0x00004000 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_BLOCK_PROC_CALL 0x00008000 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_QUICK 0x00010000 +#define I2C_FUNC_SMBUS_READ_BYTE 0x00020000 +#define I2C_FUNC_SMBUS_WRITE_BYTE 0x00040000 +#define I2C_FUNC_SMBUS_READ_BYTE_DATA 0x00080000 +#define I2C_FUNC_SMBUS_WRITE_BYTE_DATA 0x00100000 +#define I2C_FUNC_SMBUS_READ_WORD_DATA 0x00200000 +#define I2C_FUNC_SMBUS_WRITE_WORD_DATA 0x00400000 +#define I2C_FUNC_SMBUS_PROC_CALL 0x00800000 +#define I2C_FUNC_SMBUS_READ_BLOCK_DATA 0x01000000 +#define I2C_FUNC_SMBUS_WRITE_BLOCK_DATA 0x02000000 +#define I2C_FUNC_SMBUS_READ_I2C_BLOCK 0x04000000 /* I2C-like block xfer */ +#define I2C_FUNC_SMBUS_WRITE_I2C_BLOCK 0x08000000 /* w/ 1-byte reg. addr. */ +#define I2C_FUNC_SMBUS_READ_I2C_BLOCK_2 0x10000000 /* I2C-like block xfer */ +#define I2C_FUNC_SMBUS_WRITE_I2C_BLOCK_2 0x20000000 /* w/ 2-byte reg. addr. */ +#define I2C_FUNC_SMBUS_READ_BLOCK_DATA_PEC 0x40000000 /* SMBus 2.0 */ +#define I2C_FUNC_SMBUS_WRITE_BLOCK_DATA_PEC 0x80000000 /* SMBus 2.0 */ + +#define I2C_FUNC_SMBUS_BYTE I2C_FUNC_SMBUS_READ_BYTE | \ + I2C_FUNC_SMBUS_WRITE_BYTE +#define I2C_FUNC_SMBUS_BYTE_DATA I2C_FUNC_SMBUS_READ_BYTE_DATA | \ + I2C_FUNC_SMBUS_WRITE_BYTE_DATA +#define I2C_FUNC_SMBUS_WORD_DATA I2C_FUNC_SMBUS_READ_WORD_DATA | \ + I2C_FUNC_SMBUS_WRITE_WORD_DATA +#define I2C_FUNC_SMBUS_BLOCK_DATA I2C_FUNC_SMBUS_READ_BLOCK_DATA | \ + I2C_FUNC_SMBUS_WRITE_BLOCK_DATA +#define I2C_FUNC_SMBUS_I2C_BLOCK I2C_FUNC_SMBUS_READ_I2C_BLOCK | \ + I2C_FUNC_SMBUS_WRITE_I2C_BLOCK +#define I2C_FUNC_SMBUS_I2C_BLOCK_2 I2C_FUNC_SMBUS_READ_I2C_BLOCK_2 | \ + I2C_FUNC_SMBUS_WRITE_I2C_BLOCK_2 +#define I2C_FUNC_SMBUS_BLOCK_DATA_PEC I2C_FUNC_SMBUS_READ_BLOCK_DATA_PEC | \ + I2C_FUNC_SMBUS_WRITE_BLOCK_DATA_PEC +#define I2C_FUNC_SMBUS_WORD_DATA_PEC I2C_FUNC_SMBUS_READ_WORD_DATA_PEC | \ + I2C_FUNC_SMBUS_WRITE_WORD_DATA_PEC + +#define I2C_FUNC_SMBUS_READ_BYTE_PEC I2C_FUNC_SMBUS_READ_BYTE_DATA +#define I2C_FUNC_SMBUS_WRITE_BYTE_PEC I2C_FUNC_SMBUS_WRITE_BYTE_DATA +#define I2C_FUNC_SMBUS_READ_BYTE_DATA_PEC I2C_FUNC_SMBUS_READ_WORD_DATA +#define I2C_FUNC_SMBUS_WRITE_BYTE_DATA_PEC I2C_FUNC_SMBUS_WRITE_WORD_DATA +#define I2C_FUNC_SMBUS_BYTE_PEC I2C_FUNC_SMBUS_BYTE_DATA +#define I2C_FUNC_SMBUS_BYTE_DATA_PEC I2C_FUNC_SMBUS_WORD_DATA + +#define I2C_FUNC_SMBUS_EMUL I2C_FUNC_SMBUS_QUICK | \ + I2C_FUNC_SMBUS_BYTE | \ + I2C_FUNC_SMBUS_BYTE_DATA | \ + I2C_FUNC_SMBUS_WORD_DATA | \ + I2C_FUNC_SMBUS_PROC_CALL | \ + I2C_FUNC_SMBUS_WRITE_BLOCK_DATA | \ + I2C_FUNC_SMBUS_WRITE_BLOCK_DATA_PEC | \ + I2C_FUNC_SMBUS_I2C_BLOCK + +/* + * Data for SMBus Messages + */ +#define I2C_SMBUS_BLOCK_MAX 32 /* As specified in SMBus standard */ +#define I2C_SMBUS_I2C_BLOCK_MAX 32 /* Not specified but we use same structure */ +union i2c_smbus_data { + __u8 byte; + __u16 word; + __u8 block[I2C_SMBUS_BLOCK_MAX + 3]; /* block[0] is used for length */ + /* one more for read length in block process call */ + /* and one more for PEC */ +}; + +/* smbus_access read or write markers */ +#define I2C_SMBUS_READ 1 +#define I2C_SMBUS_WRITE 0 + +/* SMBus transaction types (size parameter in the above functions) + Note: these no longer correspond to the (arbitrary) PIIX4 internal codes! */ +#define I2C_SMBUS_QUICK 0 +#define I2C_SMBUS_BYTE 1 +#define I2C_SMBUS_BYTE_DATA 2 +#define I2C_SMBUS_WORD_DATA 3 +#define I2C_SMBUS_PROC_CALL 4 +#define I2C_SMBUS_BLOCK_DATA 5 +#define I2C_SMBUS_I2C_BLOCK_DATA 6 +#define I2C_SMBUS_BLOCK_PROC_CALL 7 /* SMBus 2.0 */ +#define I2C_SMBUS_BLOCK_DATA_PEC 8 /* SMBus 2.0 */ +#define I2C_SMBUS_PROC_CALL_PEC 9 /* SMBus 2.0 */ +#define I2C_SMBUS_BLOCK_PROC_CALL_PEC 10 /* SMBus 2.0 */ +#define I2C_SMBUS_WORD_DATA_PEC 11 /* SMBus 2.0 */ + + +/* ----- commands for the ioctl like i2c_command call: + * note that additional calls are defined in the algorithm and hw + * dependent layers - these can be listed here, or see the + * corresponding header files. + */ + /* -> bit-adapter specific ioctls */ +#define I2C_RETRIES 0x0701 /* number of times a device address */ + /* should be polled when not */ + /* acknowledging */ +#define I2C_TIMEOUT 0x0702 /* set timeout - call with int */ + + +/* this is for i2c-dev.c */ +#define I2C_SLAVE 0x0703 /* Change slave address */ + /* Attn.: Slave address is 7 or 10 bits */ +#define I2C_SLAVE_FORCE 0x0706 /* Change slave address */ + /* Attn.: Slave address is 7 or 10 bits */ + /* This changes the address, even if it */ + /* is already taken! */ +#define I2C_TENBIT 0x0704 /* 0 for 7 bit addrs, != 0 for 10 bit */ + +#define I2C_FUNCS 0x0705 /* Get the adapter functionality */ +#define I2C_RDWR 0x0707 /* Combined R/W transfer (one stop only)*/ +#define I2C_PEC 0x0708 /* != 0 for SMBus PEC */ +#if 0 +#define I2C_ACK_TEST 0x0710 /* See if a slave is at a specific address */ +#endif + +#define I2C_SMBUS 0x0720 /* SMBus-level access */ + +/* -- i2c.h -- */ + + +/* Note: 10-bit addresses are NOT supported! */ + +/* This is the structure as used in the I2C_SMBUS ioctl call */ +struct i2c_smbus_ioctl_data { + char read_write; + __u8 command; + int size; + union i2c_smbus_data *data; +}; + +/* This is the structure as used in the I2C_RDWR ioctl call */ +struct i2c_rdwr_ioctl_data { + struct i2c_msg *msgs; /* pointers to i2c_msgs */ + int nmsgs; /* number of i2c_msgs */ +}; + + +static inline __s32 i2c_smbus_access(int file, char read_write, __u8 command, + int size, union i2c_smbus_data *data) +{ + struct i2c_smbus_ioctl_data args; + int rc; + + args.read_write = read_write; + args.command = command; + args.size = size; + args.data = data; + + rc = ioctl(file,I2C_SMBUS,&args); + + return rc; +} + + +static inline __s32 i2c_smbus_write_quick(int file, __u8 value) +{ + return i2c_smbus_access(file,value,0,I2C_SMBUS_QUICK,NULL); +} + +static inline __s32 i2c_smbus_read_byte(int file) +{ + union i2c_smbus_data data; + if (i2c_smbus_access(file,I2C_SMBUS_READ,0,I2C_SMBUS_BYTE,&data)) + return -1; + else + return 0x0FF & data.byte; +} + +static inline __s32 i2c_smbus_write_byte(int file, __u8 value) +{ + return i2c_smbus_access(file,I2C_SMBUS_WRITE,value, + I2C_SMBUS_BYTE,NULL); +} + +static inline __s32 i2c_smbus_read_byte_data(int file, __u8 command) +{ + union i2c_smbus_data data; + if (i2c_smbus_access(file,I2C_SMBUS_READ,command, + I2C_SMBUS_BYTE_DATA,&data)) + return -1; + else + return 0x0FF & data.byte; +} + +static inline __s32 i2c_smbus_write_byte_data(int file, __u8 command, + __u8 value) +{ + union i2c_smbus_data data; + data.byte = value; + return i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_BYTE_DATA, &data); +} + +static inline __s32 i2c_smbus_read_word_data(int file, __u8 command) +{ + union i2c_smbus_data data; + if (i2c_smbus_access(file,I2C_SMBUS_READ,command, + I2C_SMBUS_WORD_DATA,&data)) + return -1; + else + return 0x0FFFF & data.word; +} + +static inline __s32 i2c_smbus_write_word_data(int file, __u8 command, + __u16 value) +{ + union i2c_smbus_data data; + data.word = value; + return i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_WORD_DATA, &data); +} + +static inline __s32 i2c_smbus_process_call(int file, __u8 command, __u16 value) +{ + union i2c_smbus_data data; + data.word = value; + if (i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_PROC_CALL,&data)) + return -1; + else + return 0x0FFFF & data.word; +} + + +/* Returns the number of read bytes */ +static inline __s32 i2c_smbus_read_block_data(int file, __u8 command, + __u8 *values) +{ + union i2c_smbus_data data; + int i; + if (i2c_smbus_access(file,I2C_SMBUS_READ,command, + I2C_SMBUS_BLOCK_DATA,&data)) + return -1; + else { + for (i = 1; i <= data.block[0]; i++) + values[i-1] = data.block[i]; + return data.block[0]; + } +} + +static inline __s32 i2c_smbus_write_block_data(int file, __u8 command, + __u8 length, __u8 *values) +{ + union i2c_smbus_data data; + int i; + if (length > 32) + length = 32; + for (i = 1; i <= length; i++) + data.block[i] = values[i-1]; + data.block[0] = length; + return i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_BLOCK_DATA, &data); +} + +/* Returns the number of read bytes */ +static inline __s32 i2c_smbus_read_i2c_block_data(int file, __u8 command, + __u8 *values) +{ + union i2c_smbus_data data; + int i; + if (i2c_smbus_access(file,I2C_SMBUS_READ,command, + I2C_SMBUS_I2C_BLOCK_DATA,&data)) + return -1; + else { + for (i = 1; i <= data.block[0]; i++) + values[i-1] = data.block[i]; + return data.block[0]; + } +} + +static inline __s32 i2c_smbus_write_i2c_block_data(int file, __u8 command, + __u8 length, __u8 *values) +{ + union i2c_smbus_data data; + int i; + if (length > 32) + length = 32; + for (i = 1; i <= length; i++) + data.block[i] = values[i-1]; + data.block[0] = length; + return i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_I2C_BLOCK_DATA, &data); +} + +/* Returns the number of read bytes */ +static inline __s32 i2c_smbus_block_process_call(int file, __u8 command, + __u8 length, __u8 *values) +{ + union i2c_smbus_data data; + int i; + if (length > 32) + length = 32; + for (i = 1; i <= length; i++) + data.block[i] = values[i-1]; + data.block[0] = length; + i = i2c_smbus_access(file,I2C_SMBUS_WRITE,command, + I2C_SMBUS_BLOCK_PROC_CALL,&data); + if ( i ) + return -1; + else { + for (i = 1; i <= data.block[0]; i++) + values[i-1] = data.block[i]; + return data.block[0]; + } +} + + +#endif /* LIB_I2CDEV_H */ + diff --git a/packages/i2c/files/i2c-io-api.h b/packages/i2c/files/i2c-io-api.h new file mode 100644 index 0000000000..35ab45865c --- /dev/null +++ b/packages/i2c/files/i2c-io-api.h @@ -0,0 +1,52 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c-io-api.h +* +* @brief This file contains definitions for performing i2c-io operations +* on the gumstix. +* +****************************************************************************/ + +#if !defined( I2C_IO_API_H ) +#define I2C_IO_API_H + +// ---- Include Files ------------------------------------------------------- + +#include +#include "i2c-io.h" + +// ---- Constants and Types ------------------------------------------------- + +// ---- Variable Externs ---------------------------------------------------- + +// ---- Function Prototypes ------------------------------------------------- + +int I2C_IO_CheckVersion( const I2C_IO_Info_t *info ); + +int I2C_IO_GetInfo( int i2cDev, I2C_IO_Info_t *info ); +int I2C_IO_GetGPIO( int i2cDev, uint8_t portNum, uint8_t *pinVal ); +int I2C_IO_SetGPIO( int i2cDev, uint8_t portNum, uint8_t pinMask, uint8_t pinVal ); +int I2C_IO_GetGPIODir( int i2cDev, uint8_t portNum, uint8_t *pinVal ); +int I2C_IO_SetGPIODir( int i2cDev, uint8_t portNum, uint8_t pinMask, uint8_t pinVal ); +int I2C_IO_GetADC( int i2cDev, uint8_t mux, uint16_t *adcVal ); +int I2C_IO_ReadReg8( int i2cDev, uint8_t reg, uint8_t *regVal ); +int I2C_IO_ReadReg16( int i2cDev, uint8_t reg, uint16_t *regVal ); +int I2C_IO_WriteReg8( int i2cDev, uint8_t reg, uint8_t regVal ); +int I2C_IO_WriteReg16( int i2cDev, uint8_t reg, uint16_t regVal ); + +#endif // I2C_IO_API_H + diff --git a/packages/i2c/files/i2c-io.h b/packages/i2c/files/i2c-io.h new file mode 100644 index 0000000000..3ffb5e9c0e --- /dev/null +++ b/packages/i2c/files/i2c-io.h @@ -0,0 +1,220 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c-io.h +* +* @brief This file defines the interface to the i2c-io program which +* runs on the robostix. +* +*****************************************************************************/ + +#if !defined( I2C_IO_H ) +#define I2C_IO_H /**< Include Guard */ + +/* ---- Include Files ---------------------------------------------------- */ + +/* ---- Constants and Types ---------------------------------------------- */ + +//--------------------------------------------------------------------------- +/** + * Defines the version of this API. This includes the layout of the + * various structures, along with the semantics associated with the + * protocol. Any changes require the version number to be incremented. + * + * Version 2 - Introduced READ/WRITE_REG_8/16 + */ + +#define I2C_IO_API_VERSION 2 + +//--------------------------------------------------------------------------- +/** + * The min version, determines the minimum version that this API is + * compatable with. This allows old host side programs to determine + * that they're not compatible. + */ + +#define I2C_IO_API_MIN_VERSION 1 + + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_GET_INFO command retrieves information about the i2c-io +* program running on the robostix. +*/ + +#define I2C_IO_GET_INFO 0x01 + +typedef struct +{ + uint8_t version; + uint8_t minVersion; + uint16_t svnRevision; + +} I2C_IO_Info_t; + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_GET_GPIO command retrieves the values of the pins indicated +* by portNum. +* +* The portNum is set such that 0 = A, 1 = B, etc. +* +* A block-reply with a single 8 bit value is returned. +*/ + +typedef struct +{ + uint8_t portNum; + +} I2C_IO_Get_GPIO_t; + +#define I2C_IO_GET_GPIO 0x02 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_SET_GPIO command sets the values of the pins specified +* by pinMask to the correponding bits in ponVal. +* +* Note: Setting a pin that's configured for input will enable a pullup +* resistor. +* +* The portNum is set such that 0 = A, 1 = B, etc. +*/ + +typedef struct +{ + uint8_t portNum; + uint8_t pinMask; + uint8_t pinVal; + +} I2C_IO_Set_GPIO_t; + +#define I2C_IO_SET_GPIO 0x03 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_GET_GPIO_DIR command retrieves the data direction +* register (DDR) for the indicated portNum. +* +* The I2C_IO_Get_GPIO_t structure is used for this command. +* +* Note: It's ok to read the values of pins which are set for output. +* +* The portNum is set such that 0 = A, 1 = B, etc. +* +* A block-reply with a single 8 bit value is returned. +* A 1 bit means that the pin is set for output and a 0 bit means that +* the pin is set for input. +*/ + +#define I2C_IO_GET_GPIO_DIR 0x04 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_SET_GPIO_DIR command sets the data direction +* register (DDR) for the indicated portNum. +* +* The I2C_IO_Set_GPIO_t structure is used for this command. +* +* The portNum is set such that 0 = A, 1 = B, etc. +*/ + +#define I2C_IO_SET_GPIO_DIR 0x05 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_GET_ADC command performs an ADC sample and returns the result. +* +* mux values 0 thru 7 read singled ended ADC values. Values 8 thru 31 +* return a variety of values. See the data sheet for specifics. +* +* A block-reply with a 16 bit value is returned, although only the +* lower 10 bits are significant. +*/ + +typedef struct +{ + uint8_t mux; + +} I2C_IO_Get_ADC_t; + +#define I2C_IO_GET_ADC 0x06 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_READ_REG_8 command reads a 8-bit register. +* +* A block reply with an 8 bit value is returned. +*/ + +typedef struct +{ + uint8_t reg; ///< Index of the register to be read. + +} I2C_IO_ReadReg8_t; + +#define I2C_IO_READ_REG_8 0x07 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_READ_REG_16 command reads a 16-bit register. +* +* A block reply with a 16 bit value is returned. +*/ + +typedef struct +{ + uint8_t reg; ///< Index of the register to be read. + +} I2C_IO_ReadReg16_t; + +#define I2C_IO_READ_REG_16 0x08 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_WRITE_REG_8 command writes an 8-bit register. +*/ + +typedef struct +{ + uint8_t reg; ///< Index of the register to be read. + uint8_t val; ///< Value to write into the register + +} I2C_IO_WriteReg8_t; + +#define I2C_IO_WRITE_REG_8 0x09 + +//--------------------------------------------------------------------------- +/** +* The I2C_IO_WRITE_REG_16 command writes a 16-bit register. +*/ + +typedef struct +{ + uint8_t reg; ///< Index of the register to be read. + uint8_t pad; ///< Pad for alignment on the host. + uint16_t val; ///< Value to write + +} I2C_IO_WriteReg16_t; + +#define I2C_IO_WRITE_REG_16 0x0A + +/* ---- Variable Externs ------------------------------------------------- */ + +/* ---- Function Prototypes ---------------------------------------------- */ + +#endif /* I2C_IO_H */ + diff --git a/packages/i2c/files/i2c.c b/packages/i2c/files/i2c.c new file mode 100644 index 0000000000..9f0bafdba1 --- /dev/null +++ b/packages/i2c/files/i2c.c @@ -0,0 +1,710 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c.c +* +* @brief This program allows basic i2c commands to be sent out the i2c +* bus, +* +****************************************************************************/ + +// ---- Include Files ------------------------------------------------------- + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "i2c-dev.h" +#include "i2c-api.h" +#include "i2c-io-api.h" +#include "Log.h" + +// #include "svn-version.h" + +// ---- Public Variables ---------------------------------------------------- +// ---- Private Constants and Types ----------------------------------------- + +// ---- Private Variables --------------------------------------------------- + +enum +{ + OPT_MEM_DEFAULT = 0, + + // Options assigned a single character code can use that charater code + // as a short option. + + OPT_COUNT = 'c', + + // Options from this point onwards don't have any short option equivalents + + OPT_FIRST_LONG_OPT = 0x80, + + OPT_HELP, + OPT_VERSION, +}; + +enum +{ + CMD_DEFAULT, + + CMD_READ_BYTE, + CMD_READ_BYTE_2, + CMD_READ_BYTE_4, + + CMD_WRITE_BYTE, + CMD_WRITE_BYTE_2, + CMD_WRITE_BYTE_4, + + CMD_RECV_BYTE, + CMD_RECV_BYTE_2, + CMD_RECV_BYTE_4, + + CMD_SEND_BYTE, + CMD_SEND_BYTE_2, + CMD_SEND_BYTE_4, +}; + +struct +{ + int cmd; + const char *cmdStr; + +} gCmdMap[] = +{ + { CMD_READ_BYTE, "ReadByte" }, + { CMD_READ_BYTE, "rb" }, + { CMD_READ_BYTE_2, "ReadByte2" }, + { CMD_READ_BYTE_2, "rb2" }, + { CMD_READ_BYTE_4, "ReadByte4" }, + { CMD_READ_BYTE_4, "rb4" }, + + { CMD_WRITE_BYTE, "WriteByte" }, + { CMD_WRITE_BYTE, "wb" }, + { CMD_WRITE_BYTE_2, "WriteByte2" }, + { CMD_WRITE_BYTE_2, "wb2" }, + { CMD_WRITE_BYTE_4, "WriteByte4" }, + { CMD_WRITE_BYTE_4, "wb4" }, + + { CMD_RECV_BYTE, "RecvByte" }, + { CMD_RECV_BYTE, "vb" }, + { CMD_RECV_BYTE_2, "RecvByte2" }, + { CMD_RECV_BYTE_2, "vb2" }, + { CMD_RECV_BYTE_4, "RecvByte4" }, + { CMD_RECV_BYTE_4, "vb4" }, + + { CMD_SEND_BYTE, "SendByte" }, + { CMD_SEND_BYTE, "sb" }, + { CMD_SEND_BYTE_2, "SendByte2" }, + { CMD_SEND_BYTE_2, "sb2" }, + { CMD_SEND_BYTE_4, "SendByte4" }, + { CMD_SEND_BYTE_4, "sb4" }, +}; + +int gNumCmds = sizeof( gCmdMap ) / sizeof( gCmdMap[ 0 ]); + +int gI2cAddr = -1; +int gByteCount = 1; + +const char *gCmdStr; +int gCmd = CMD_DEFAULT; +const char *gAddrStr = NULL; +const char *gDataStr = NULL; + +struct option gOption[] = +{ + { "count", required_argument, NULL, OPT_COUNT }, + { "version", no_argument, NULL, OPT_VERSION }, + { "verbose", no_argument, &gVerbose, 1 }, + { "debug", no_argument, &gDebug, 1 }, + { "help", no_argument, NULL, OPT_HELP }, + { NULL } +}; + +#define TRUE 1 +#define FALSE 0 + +typedef enum +{ + NoADC, + AllowADC, + +} AllowADC_t; + +#define ADC_PORT 8 + +// ---- Private Function Prototypes ----------------------------------------- + +static int ParseByte( const char *byteStr, uint8_t *byte ); +static int ParseBytes( const char *byteStr, uint8_t *byte, uint8_t maxBytes, uint8_t *bytesParsed ); + +static void ProcessReadByteCommand( int i2cDev, const char *addrStr ); +static void ProcessWriteByteCommand( int i2cDev, const char *addrStr, const char *dataStr ); +static void ProcessRecvByteCommand( int i2cDev ); +static void ProcessSendByteCommand( int i2cDev, const char *dataStr ); +static void Usage( void ); + +// ---- Functions ----------------------------------------------------------- + +//*************************************************************************** +/** +* Main entry point +*/ + +int main( int argc, char **argv ) +{ + char shortOptsStr[ sizeof( gOption ) / sizeof( gOption[ 0 ] ) + 1 ]; + char *shortOpts = shortOptsStr; + struct option *scanOpt; + int opt; + const char *i2cDevName = "/dev/i2c-0"; + int i2cDev; + int cmdIdx; + + LogInit( stdout ); + + // Figure out the short options from our options structure + + for ( scanOpt = gOption; scanOpt->name != NULL; scanOpt++ ) + { + if (( scanOpt->flag == NULL ) && ( scanOpt->val < OPT_FIRST_LONG_OPT )) + { + *shortOpts++ = (char)scanOpt->val; + + if ( scanOpt->has_arg != no_argument ) + { + *shortOpts++ = ':'; + } + } + } + *shortOpts++ = '\0'; + + // Parse the command line options + + while (( opt = getopt_long( argc, argv, shortOptsStr, gOption, NULL )) != -1 ) + { + switch ( opt ) + { + case 0: + { + // getopt_long returns 0 for entries where flag is non-NULL + + break; + } + + case OPT_COUNT: + { + gByteCount = (int)strtol( optarg, NULL, 0 ); + if ( gByteCount <= 0 ) + { + LogError( "Expecting byte count >= 0, found: '%s'\n", optarg ); + Usage(); + exit( 1 ); + } + if ( gByteCount > I2C_MAX_DATA_LEN ) + { + LogError( "Max byte count supported: %d, found %d\n", I2C_MAX_DATA_LEN, gByteCount ); + Usage(); + exit( 1 ); + } + break; + } + +// case OPT_VERSION: +// { +// Log( "i2c SVN Revision: %d\n", SVN_REVISION ); +// exit( 0 ); +// break; +// } + + case '?': + case OPT_HELP: + default: + { + LogError( "opt:%d\n", opt ); + Usage(); + exit( 1 ); + } + } + } + argc -= optind; + argv += optind; + + // Verify that an i2c-address was specified + + if ( argc < 1 ) + { + LogError( "Must specify an i2c address\n\n" ); + Usage(); + exit( 1 ); + } + gI2cAddr = strtol( argv[ 0 ], NULL, 0 ); + if (( gI2cAddr <= 0 ) || ( gI2cAddr > 127 )) + { + LogError( "Expecting i2c address in the range of 1-127, Found: %d\n", gI2cAddr ); + Usage(); + exit( 1 ); + } + + // Verify that a command has been specified + + if ( argc < 2 ) + { + LogError( "Must specify a command\n" ); + Usage(); + exit( 1 ); + } + gCmdStr = argv[ 1 ]; + for ( cmdIdx = 0; cmdIdx < gNumCmds; cmdIdx++ ) + { + if ( strcasecmp( gCmdStr, gCmdMap[ cmdIdx ].cmdStr ) == 0 ) + { + gCmd = gCmdMap[ cmdIdx ].cmd; + break; + } + } + if ( gCmd == CMD_DEFAULT ) + { + LogError( "Unrecognized command '%s'\n", gCmdStr ); + exit( 1 ); + } + + // Process command specific arguments + + if (( gCmd == CMD_READ_BYTE_2 ) + || ( gCmd == CMD_WRITE_BYTE_2 ) + || ( gCmd == CMD_RECV_BYTE_2 ) + || ( gCmd == CMD_SEND_BYTE_2 )) + { + gByteCount = 2; + } + else + if (( gCmd == CMD_READ_BYTE_4 ) + || ( gCmd == CMD_WRITE_BYTE_4 ) + || ( gCmd == CMD_RECV_BYTE_4 ) + || ( gCmd == CMD_SEND_BYTE_4 )) + { + gByteCount = 4; + } + + if (( gCmd == CMD_READ_BYTE ) + || ( gCmd == CMD_READ_BYTE_2 ) + || ( gCmd == CMD_READ_BYTE_4 )) + { + if ( argc < 3 ) + { + LogError( "Expecting address\n" ); + Usage(); + exit( 1 ); + } + if ( argc > 3 ) + { + LogError( "Unexpected extra parameters\n" ); + Usage(); + exit( 1 ); + } + + gAddrStr = argv[ 2 ]; + } + else + if (( gCmd == CMD_WRITE_BYTE ) + || ( gCmd == CMD_WRITE_BYTE_2 ) + || ( gCmd == CMD_WRITE_BYTE_4 )) + { + if ( argc < 4 ) + { + LogError( "Expecting address and data\n" ); + Usage(); + exit( 1 ); + } + if ( argc > 4 ) + { + LogError( "Unexpected extra parameters\n" ); + Usage(); + exit( 1 ); + } + + gAddrStr = argv[ 2 ]; + gDataStr = argv[ 3 ]; + } + else + if (( gCmd == CMD_RECV_BYTE ) + || ( gCmd == CMD_RECV_BYTE_2 ) + || ( gCmd == CMD_RECV_BYTE_4 )) + { + if ( argc > 2 ) + { + LogError( "Unexpected extra parameters\n" ); + Usage(); + exit( 1 ); + } + } + else + if (( gCmd == CMD_SEND_BYTE ) + || ( gCmd == CMD_SEND_BYTE_2 ) + || ( gCmd == CMD_SEND_BYTE_4 )) + { + if ( argc < 3 ) + { + LogError( "Expecting data\n" ); + Usage(); + exit( 1 ); + } + if ( argc > 3 ) + { + LogError( "Unexpected extra parameters\n" ); + Usage(); + exit( 1 ); + } + gDataStr = argv[ 2 ]; + } + + if ( gDebug ) + { + Log( "i2cAddr:0x%02x Cmd: %s (%d)", gI2cAddr, gCmdStr, gCmd ); + if ( gAddrStr != NULL ) + { + Log( " Addr: %s", gAddrStr ); + } + if ( gDataStr != NULL ) + { + Log( " Data: %s", gDataStr ); + } + Log( "\n" ); + } + + // Try to open the i2c device + + if (( i2cDev = open( i2cDevName, O_RDWR )) < 0 ) + { + LogError( "Error opening '%s': %s\n", i2cDevName, strerror( errno )); + exit( 1 ); + } + + // Indicate which slave we wish to speak to + + I2cSetSlaveAddress( i2cDev, gI2cAddr, I2C_NO_CRC ); + + switch ( gCmd ) + { + case CMD_READ_BYTE: + case CMD_READ_BYTE_2: + case CMD_READ_BYTE_4: + { + ProcessReadByteCommand( i2cDev, gAddrStr ); + break; + } + + case CMD_WRITE_BYTE: + case CMD_WRITE_BYTE_2: + case CMD_WRITE_BYTE_4: + { + ProcessWriteByteCommand( i2cDev, gAddrStr, gDataStr ); + break; + } + + case CMD_RECV_BYTE: + case CMD_RECV_BYTE_2: + case CMD_RECV_BYTE_4: + { + ProcessRecvByteCommand( i2cDev ); + break; + } + + case CMD_SEND_BYTE: + case CMD_SEND_BYTE_2: + case CMD_SEND_BYTE_4: + { + ProcessSendByteCommand( i2cDev, gDataStr ); + break; + } + } + + close( i2cDev ); + + return 0; + +} // main + +//*************************************************************************** +/** +* Parse a string looking for a single byte. +*/ + +int ParseByte( const char *byteStr, uint8_t *byte ) +{ + char *endPtr; + + *byte = (uint8_t)strtol( byteStr, &endPtr, 0 ); + + if ( *endPtr != '\0' ) + { + LogError( "Expecting numeric value, found '%s'\n", byteStr ); + return FALSE; + } + + return TRUE; + +} // ParseByte + +//*************************************************************************** +/** +* Parse a string looking for an array of bytes. +*/ + +int ParseBytes( const char *byteStr, uint8_t *byte, uint8_t maxBytes, uint8_t *bytesParsed ) +{ + char *endPtr; + + if (( byteStr[ 0 ] == '0' ) && ( byteStr[ 1 ] == 'x' )) + { + const char *s = &byteStr[ 2 ]; + *bytesParsed = 0; + + // Could be a multi-byte hex string + + while ( *s != '\0' ) + { + if ( *bytesParsed >= maxBytes ) + { + LogError( "Too many bytes, max: %d\n", maxBytes ); + return FALSE; + } + + (*bytesParsed)++; + *byte = 0; + + if (( *s >= 'A' ) && ( *s <= 'F' )) + { + *byte = *s - 'A' + 10; + } + else + if (( *s >= 'a' ) && ( *s <= 'f' )) + { + *byte = *s - 'a' + 10; + } + else + if (( *s >= '0' ) && ( *s <= '9' )) + { + *byte = *s - '0'; + } + else + { + LogError( "Expecting hex digit, found '%c'\n", *s ); + return FALSE; + } + s++; + + if ( *s == '\0' ) + { + break; + } + + *byte <<= 4; + if (( *s >= 'A' ) && ( *s <= 'F' )) + { + *byte |= *s - 'A' + 10; + } + else + if (( *s >= 'a' ) && ( *s <= 'f' )) + { + *byte |= *s - 'a' + 10; + } + else + if (( *s >= '0' ) && ( *s <= '9' )) + { + *byte |= *s - '0'; + } + else + { + LogError( "Expecting hex digit, found '%c'\n", *s ); + return FALSE; + } + s++; + byte++; + } + } + else + { + // It's decimal or octal - only a single byte + + *byte = (uint8_t)strtol( byteStr, &endPtr, 0 ); + + if ( *endPtr != '\0' ) + { + LogError( "Expecting numeric value, found '%s'\n", byteStr ); + return FALSE; + } + *bytesParsed = 1; + } + + return TRUE; + +} // ParseBytes + +//*************************************************************************** +/** +* Issues a read byte command to read a byte from a particular address. +*/ + +void ProcessReadByteCommand( int i2cDev, const char *addrStr ) +{ + uint8_t addr; + uint8_t dataByte[ I2C_MAX_DATA_LEN ]; + int rc; + int i; + + if ( !ParseByte( addrStr, &addr )) + { + return; + } + + if (( rc = I2cReadBytes( i2cDev, addr, dataByte, gByteCount )) != 0 ) + { + LogError( "I2cReadByte failed: %d\n", rc ); + return; + } + + Log( "0x", dataByte[0] ); + + for ( i = 0; i < gByteCount; i++ ) + { + Log( "%02x", dataByte[i] ); + } + Log( "\n" ); + +} // ProcessReadByteCommand + +//*************************************************************************** +/** +* Issues a recv byte command to read bytes with no address. +*/ + +void ProcessRecvByteCommand( int i2cDev ) +{ + uint8_t dataByte[ I2C_MAX_DATA_LEN ]; + int rc; + int i; + + if (( rc = I2cReceiveBytes( i2cDev, dataByte, gByteCount )) != 0 ) + { + LogError( "I2cRecvBytes failed: %d\n", rc ); + return; + } + + Log( "0x", dataByte[0] ); + + for ( i = 0; i < gByteCount; i++ ) + { + Log( "%02x", dataByte[i] ); + } + Log( "\n" ); + +} // ProcessRecvByteCommand + +//*************************************************************************** +/** +* Issues a write byte command to write a byte to a particular address. +*/ + +void ProcessWriteByteCommand( int i2cDev, const char *addrStr, const char *dataStr ) +{ + uint8_t addr; + uint8_t dataByte[ I2C_MAX_DATA_LEN ]; + uint8_t bytesParsed; + int rc; + + if ( !ParseByte( addrStr, &addr )) + { + return; + } + + if ( !ParseBytes( dataStr, dataByte, sizeof( dataByte ), &bytesParsed )) + { + return; + } + + if (( rc = I2cWriteBytes( i2cDev, addr, dataByte, bytesParsed )) != 0 ) + { + LogError( "I2cWriteBytes failed: %d\n", rc ); + return; + } + +} // ProcessWriteByteCommand + +//*************************************************************************** +/** +* Issues a send byte command to write bytes with no address specified. +*/ + +void ProcessSendByteCommand( int i2cDev, const char *dataStr ) +{ + uint8_t dataByte[ I2C_MAX_DATA_LEN ]; + uint8_t bytesParsed; + int rc; + + if ( !ParseBytes( dataStr, dataByte, sizeof( dataByte ), &bytesParsed )) + { + return; + } + + if (( rc = I2cSendBytes( i2cDev, dataByte, bytesParsed )) != 0 ) + { + LogError( "I2cSendBytes failed: %d\n", rc ); + return; + } + +} // ProcessSendByteCommand + +//*************************************************************************** +/** +* Usage +*/ + +void Usage( void ) +{ + fprintf( stderr, "Usage: i2c [options] i2c-addr cmd [cmd-arguments]\n" ); + fprintf( stderr, "Send I2C commands\n" ); + fprintf( stderr, "\n" ); + fprintf( stderr, "The following commands are supported:\n" ); + fprintf( stderr, "ReadByte addr Retrieves byte(s) starting at the indicated address\n" ); + fprintf( stderr, "WriteByte addr data Write byte(s) starting at the indicated address\n" ); + fprintf( stderr, "ReadByte2 addr Retrieves two bytes from the indicated address\n" ); + fprintf( stderr, "WriteByte2 addr data Writes two bytes into the indicated address\n" ); + fprintf( stderr, "ReadByte4 addr Retrieves four bytes from the indicated address\n" ); + fprintf( stderr, "WriteByte4 addr data Writes four bytes into the indicated address\n" ); + fprintf( stderr, "RecvByte Retrieves byte(s)(no address specified)\n" ); + fprintf( stderr, "SendByte data Writes byte(s)(no address specified)\n" ); + fprintf( stderr, "RecvByte2 Retrieves 2 bytes (no address specified)\n" ); + fprintf( stderr, "SendByte2 data Writes 2 bytes(no address specified)\n" ); + fprintf( stderr, "RecvByte4 Retrieves 4 bytes (no address specified)\n" ); + fprintf( stderr, "SendByte4 data Writes 4 bytes(no address specified)\n" ); + fprintf( stderr, "\n" ); + fprintf( stderr, "The above commands can be shortened to rb, wb, rb2, wb2, rb4, wb4, vb, sd, vb2 sb2 vb4, and sb4 \n" ); + fprintf( stderr, "respectively.\n" ); + fprintf( stderr, "\n" ); + fprintf( stderr, "The following options may be used:\n" ); + fprintf( stderr, "--count=n Specifies how many bytes to read for ReadByte or RecvByte\n" ); + fprintf( stderr, "--version Prints the SVN version of this program\n" ); + fprintf( stderr, "--verbose Print additional information\n" ); + fprintf( stderr, "--help Prints this information\n" ); +} + diff --git a/packages/i2c/files/i2c.h b/packages/i2c/files/i2c.h new file mode 100644 index 0000000000..bbfd276cec --- /dev/null +++ b/packages/i2c/files/i2c.h @@ -0,0 +1,135 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* @file i2c.h +* +* @brief Global definitions for interfacing with the AVR TWI (aka I2C) +* hardware +* +****************************************************************************/ +/** +* @defgroup xxx Readable version of xxx. +* +* @brief Brief description of what xxx does. +* +* Longer description of what xxx does. +* +****************************************************************************/ + +#if !defined( I2C_H ) +#define I2C_H /**< Include Guard */ + +/* ---- Include Files ---------------------------------------------------- */ + +#include + +#if !defined( CONFIG_H ) +# include "Config.h" +#endif + + +/** + * @addtogroup I2C + * @{ + */ + +/* ---- Constants and Types ---------------------------------------------- */ + +/** + * Error Codes + */ + +#define I2C_ERROR_NONE 0 // No Error +#define I2C_ERROR_ADDR_NACK -1 // No response to SLA+R/W +#define I2C_ERROR_DATA_NACK -2 // NACK during data transmission +#define I2C_ERROR_ARBITRATION_LOST -3 // Lost arbitration +#define I2C_ERROR_BAD_LEN -4 // Length is wonky +#define I2C_ERROR_BAD_CRC -5 // CRC failed +#define I2C_ERROR_BUS_ERROR -6 // Someting weird on the i2c bus + +typedef int8_t I2C_Error_t; + +/** + * Since we're loosely following the SMBus spec, we restrict the amount + * of data in each transaction to 32 bytes. + */ + +#define I2C_MAX_DATA_LEN 32 + +/** + * I2C_Addr_t can contain the address of any device on the bus. This + * module only supports 7 bit addressing. + */ + +typedef uint8_t I2C_Addr_t; + +/** + * The I2C_CRC macro can be used to remove all CRC support at compile time. + */ + +#if CFG_I2C_USE_CRC +# define I2C_CRC(x) x +#else + +# define I2C_CRC(x) +#endif + + +/** + * I2C_Data_t encapsulates the data being read or written on the i2c bus. + * This module follows the SMBus spec, whihch specifies a maximum payload + * of 32 bytes. + */ + +typedef struct +{ +#if CFG_I2C_USE_CRC + uint8_t m_crc; +#endif + + + // For reads, m_len is the number of bytes actually read (doesn't include + // the CRC - if present). If a block transfer was performed which has a + // length byte, this length will include the length byte. + + uint8_t m_len; + + // Note: Under SMBus, a block write can consist of a command, a length, + // 32 bytes of payload, and a CRC. + // + // A read response can consist of a length, 32 bytes of data, and a CRC. + + uint8_t m_data[ I2C_MAX_DATA_LEN + 2]; // +1 for the command, +1 for length + +} I2C_Data_t; + +/* ---- Variable Externs ------------------------------------------------- */ + +/** + * Description of variable. + */ + +/* ---- Function Prototypes ---------------------------------------------- */ + +/* + * Just include prototypes here. Put full descriptions in the .c files. + */ + +/** @} */ + +#endif /* I2C_H */ + + diff --git a/packages/i2c/files/i2c.init b/packages/i2c/files/i2c.init new file mode 100755 index 0000000000..957ce68c7b --- /dev/null +++ b/packages/i2c/files/i2c.init @@ -0,0 +1,37 @@ +#!/bin/sh +# +# Start i2c support +# + +start() { + echo "Starting i2c..." + + /sbin/modprobe i2c-pxa + /sbin/modprobe i2c-dev +} +stop() { + echo "Stopping i2c..." + +} +restart() { + stop + start +} + +case "$1" in + start) + start + ;; + stop) + stop + ;; + restart) + restart + ;; + *) + echo $"Usage: $0 {start|stop|restart}" + exit 1 +esac + +exit $? + diff --git a/packages/i2c/i2c.bb b/packages/i2c/i2c.bb new file mode 100644 index 0000000000..69b4c1cc32 --- /dev/null +++ b/packages/i2c/i2c.bb @@ -0,0 +1,45 @@ +DESCRIPTION = "i2c init file and command line tool" +SECTION = "base" +PRIORITY = "required" +PR = "r2" + +SRC_URI = " \ + file://Config.h \ + file://Crc8.h \ + file://Crc8.c \ + file://DumpMem.h \ + file://DumpMem.c \ + file://Log.h \ + file://Log.c \ + file://i2c-api.h \ + file://i2c-api.c \ + file://i2c-dev.h \ + file://i2c-io.h \ + file://i2c-io-api.h \ + file://i2c.h \ + file://i2c.c \ + file://i2c.init \ + " + +S = "${WORKDIR}" + +do_compile () { + ${CC} -o i2c *.c +} + +do_install () { + install -d ${D}${bindir}/ + install -m 0755 ${WORKDIR}/i2c ${D}${bindir}/ + + install -d ${D}${sysconfdir}/init.d/ + install -m 0755 ${WORKDIR}/i2c.init ${D}${sysconfdir}/init.d/i2c +} + +inherit update-rc.d +INITSCRIPT_NAME = "i2c" +INITSCRIPT_PARAMS = "defaults 90" + +PACKAGES = "${PN}" +FILES_${PN} = "${bindir}/*" +FILES_${PN} += "${sysconfdir}/*" + diff --git a/packages/microwindows/files/defconfig b/packages/microwindows/files/defconfig new file mode 100644 index 0000000000..4b3607f3e8 --- /dev/null +++ b/packages/microwindows/files/defconfig @@ -0,0 +1,381 @@ +#################################################################### +# Microwindows and Nano-X configuration file +# +# This package can be configured to run on Linux (MIPS, ARM, POWERPC or x86) +# UNIX, ELKS, DJGPP, or RTEMS. +# On Linux, we've got drivers for Linux 2.x framebuffers, X11, or, +# svgalib for VGA hardware. +# In addition, a gpm or direct serial mouse driver can be configured. +# On ELKS, the bios screen driver and serial mouse driver are always used. +# +# Either Microwindows and/or Nano-X can be built. +# Microwindows and Nano-X have several demos. +# +# For MSDOS makes, see mcmwin.mak and mcnanox.mak +#################################################################### + +#################################################################### +# +# build target platform +# +# Valid ARCH values are: +# +# LINUX-NATIVE +# LINUX-TCC +# LINUX-ARM +# LINUX-MIPS +# LINUX-POWERPC (BIGENDIAN=Y) +# LINUX-SPARC (BIGENDIAN=Y) +# LINUX-SH +# FREEBSD-X86 +# SOLARIS (BIGENDIAN=Y) +# TRIMEDIA +# RTEMS +# DJGPP +# ELKS +# +# note: ELKS can't build client/server nano-X, nor widget lib +# +#################################################################### +ARCH = LINUX-ARM +BIGENDIAN = N +NATIVETOOLSPREFIX = + +#################################################################### +# +# Compiling options +# +#################################################################### +OPTIMIZE = Y +DEBUG = N +VERBOSE = N +THREADSAFE = Y +GPROF = N + +#################################################################### +# +# Libraries to build: microwin, nano-X, nanowidget, object frameworks +# +#################################################################### +MICROWIN = N +NANOX = Y +SHAREDLIBS = Y +OBJFRAMEWORK = N + + +#################################################################### +# +# Demos to build +# +#################################################################### +MICROWINDEMO = N +NANOXDEMO = Y + +#################################################################### +# +# Applications to build +# +#################################################################### +NANOWM = Y + +#################################################################### +# +# The pixeltype of the native hardware or underlying graphics library. +# This definition defines the PIXELVAL to be 32, 16 or 8 bits wide. +# If using Linux framebuffer, set to MWPF_TRUECOLOR0888, and use fbset. +# It also enables GdArea/GrArea for this particular pixel packing format. +# +# define MWPF_PALETTE /* pixel is packed 8 bits 1, 4 or 8 pal index*/ +# define MWPF_TRUECOLOR8888 /* pixel is packed 32 bits 8/8/8/8 truecolor w/alpha*/ +# define MWPF_TRUECOLOR0888 /* pixel is packed 32 bits 8/8/8 truecolor*/ +# define MWPF_TRUECOLOR888 /* pixel is packed 24 bits 8/8/8 truecolor*/ +# define MWPF_TRUECOLOR565 /* pixel is packed 16 bits 5/6/5 truecolor*/ +# define MWPF_TRUECOLOR555 /* pixel is packed 16 bits 5/5/5 truecolor*/ +# define MWPF_TRUECOLOR332 /* pixel is packed 8 bits 3/3/2 truecolor*/ +# +#################################################################### +SCREEN_PIXTYPE = MWPF_TRUECOLOR565 + +#################################################################### +# +# NanoX: Put Y to the following line to link the nano-X application +# with the server. This is required for ELKS, if no network is present, +# or for speed or debugging. This affects the nano-X server only. +# +#################################################################### +LINK_APP_INTO_SERVER = N + +#################################################################### +# Shared memory support for Nano-X client/server protocol speedup +#################################################################### +HAVE_SHAREDMEM_SUPPORT = N + +#################################################################### +# +# File I/O support +# Supporting either below drags in libc stdio, which may not be wanted +# +#################################################################### +HAVE_FILEIO = Y + +#################################################################### +# BMP, GIF reading support +#################################################################### +HAVE_BMP_SUPPORT = Y +HAVE_GIF_SUPPORT = Y +HAVE_PNM_SUPPORT = N +HAVE_XPM_SUPPORT = N + +#################################################################### +# JPEG support through libjpeg, see README.txt in contrib/jpeg +#################################################################### +HAVE_JPEG_SUPPORT = Y +INCJPEG = +LIBJPEG = + +#################################################################### +# PNG support via libpng and libz +#################################################################### +HAVE_PNG_SUPPORT = N +INCPNG = +LIBPNG = +LIBZ = + +#################################################################### +# TIFF support through libtiff +#################################################################### +HAVE_TIFF_SUPPORT = N +INCTIFF = . +LIBTIFF = /usr/lib/libtiff.a + +#################################################################### +# native .fnt loadable font support +#################################################################### +HAVE_FNT_SUPPORT = N +HAVE_FNTGZ_SUPPORT = N +FNT_FONT_DIR = "fonts/bdf" + +#################################################################### +# T1 adobe type1 font support thru t1lib +#################################################################### +HAVE_T1LIB_SUPPORT = N +INCT1LIB = . +LIBT1LIB = /usr/lib/libt1.a + +#################################################################### +# TrueType font support thru FreeType 1.x +#################################################################### +HAVE_FREETYPE_SUPPORT = N +INCFTLIB = /usr/include/freetype1 +LIBFTLIB = /usr/lib/libttf.so +FREETYPE_FONT_DIR = "fonts/truetype" + +#################################################################### +# Support for many kinds of font thru FreeType 2.x +# Must also set FREETYPE_FONT_DIR in the Freetype 1.x section +#################################################################### +HAVE_FREETYPE_2_SUPPORT = N +INCFT2LIB = . +LIBFT2LIB = /gumstix/gumstix-buildroot/build_arm_nofpu/staging_dir/usr/lib/libfreetype.a + +#################################################################### +# PCF font support +# Selecting HAVE_PCFGZ_SUPPORT will allow you to directly read +# .pcf.gz files, but it will add libz to the size of the server +#################################################################### +HAVE_PCF_SUPPORT = N +HAVE_PCFGZ_SUPPORT = N +PCF_FONT_DIR = "fonts/pcf" + +#################################################################### +# Chinese Han Zi Ku loadable font support +#################################################################### +HAVE_HZK_SUPPORT = N +HZK_FONT_DIR = "fonts/chinese" + +#################################################################### +# Chinese BIG5 compiled in font support (big5font.c) +#################################################################### +HAVE_BIG5_SUPPORT = N + +#################################################################### +# Chinese GB2312 compiled in font support (gb2312font.c) +#################################################################### +HAVE_GB2312_SUPPORT = N + +#################################################################### +# Japanese JISX0213 compiled in font support (jisx0213-12x12.c) +#################################################################### +HAVE_JISX0213_SUPPORT = N + +#################################################################### +# Korean HANGUL font support (jo16x16.c) +#################################################################### +HAVE_KSC5601_SUPPORT = N + +#################################################################### +# Japanese EUC-JP support using loadable MGL font +#################################################################### +HAVE_EUCJP_SUPPORT = N +EUCJP_FONT_DIR = "fonts/japanese" + +#################################################################### +# Generate screen driver interface only with no fonts or clipping +#################################################################### +NOFONTSORCLIPPING = N + +#################################################################### +# +# Window move algorithms for Microwindows +# Change for tradeoff between cpu speed and looks +# ERASEMOVE repaints only backgrounds while window dragging, quicker. +# Otherwise an XOR redraw is used for window moves only after button up, +# quickest (should set for ELKS) +# UPDATEREGIONS paints in update clipping region only for better look and feel +# +#################################################################### +ERASEMOVE = Y +UPDATEREGIONS = Y + +#################################################################### +# +# Link with Gray Palette (valid only for 4bpp modes) +# +#################################################################### +GRAYPALETTE = N + +#################################################################### +# +# If the platform is running UNIX, Linux or RTEMS... +# +#################################################################### +ifneq ($(ARCH), ELKS) + +# X Window screen, mouse and kbd drivers +X11 = N + +ifeq ($(X11), Y) +# startup screen width, height, (depth for palette mode only) +SCREEN_WIDTH = 480 +SCREEN_HEIGHT = 640 +SCREEN_DEPTH = 16 + +# You may want to turn this on for XFree86 4.x or if your backing store +# isn't functioning properly +USE_EXPOSURE = Y + +else + +# framebuffer screen driver (linear and/or vga 4 planes) +# set VTSWITCH to include virtual terminal switch code +# set FBREVERSE to reverse bit orders in 1,2,4 bpp +# set FBVGA=N for all systems without VGA hardware (for MIPS must=N) +FRAMEBUFFER = Y +FBVGA = N +VTSWITCH = N +FBREVERSE = N + +# set HAVETEXTMODE=Y for systems that can switch between text & graphics. +# On a graphics-only embedded system, such as Osprey and Embedded +# Planet boards, set HAVETEXTMODE=N +HAVETEXTMODE = N + +# svgalib screen driver +VGALIB = N + +# direct VGA hardware access screen driver +HWVGA = N + +#################################################################### +# Mouse drivers +# GPMMOUSE gpm mouse +# SERMOUSE serial Microsoft, PC, Logitech, PS/2 mice (/dev/psaux) +# SUNMOUSE Sun Workstation mouse (/dev/sunmouse) +# NOMOUSE no mouse driver +# +# Touchscreen drivers +# IPAQMOUSE Compaq iPAQ, Intel Assabet (/dev/h3600_tsraw) +# ZAURUSMOUSE Sharp Zaurus (/dev/sharp_ts) +# TUXMOUSE TuxScreen (/dev/ucb1x00-ts) +# ADSMOUSE Applied Data Systems GC+ (/dev/ts) +# ADS7846MOUSE ADS7846 chip, PSI OMAP Innovator (/dev/innnovator_ts) +# EPMOUSE Embedded Planet (/dev/tpanel) +# VHMOUSE Vtech Helio (/dev/tpanel) +# MTMOUSE MicroTouch serial (/dev/ttyS1) +# PSIONMOUSE Psion 5 (/dev/touch_psion) +# YOPYMOUSE Yopy (/dev/yopy-ts) +# HARRIERMOUSE NEC Harrier (/dev/tpanel) +#################################################################### +GPMMOUSE = N +SERMOUSE = Y +SUNMOUSE = N +NOMOUSE = N +IPAQMOUSE = N +ZAURUSMOUSE = N +TUXMOUSE = N +ADSMOUSE = N +ADS7846MOUSE = N +EPMOUSE = N +VHMOUSE = N +MTMOUSE = N +PSIONMOUSE = N +YOPYMOUSE = N +HARRIERMOUSE = N +LIRCMOUSE = N + +# keyboard or null kbd driver +TTYKBD = N +SCANKBD = N +PIPEKBD = N +IPAQKBD = N +LIRCKBD = N +NOKBD = Y + +endif + +# Secondary keyboard drivers. +# You may have a normal keyboard driver in addition to these +# drivers, e.g. for both normal keyboard and IR input. +LIRCKBD2 = N + +#################################################################### +# Screen driver specific configuration +# SA1100_LCD_LTLEND 4bpp driver with arm SA1100 LCD controller +# INVERT4BPP 4bpp inverted pixel driver for VTech Helio +#################################################################### +SA1100_LCD_LTLEND = N +INVERT4BPP = N + +#################################################################### +# +# If the platform is a RTEMS box .... +# +#################################################################### +ifeq ($(ARCH), RTEMS) + +# Location & BSP information of the RTEMS build +RTEMS_BUILD = /tools/build-i386-elf-rtems +RTEMS_BSP = pc386 +LINK_APP_INTO_SERVER = Y + +endif + +endif + +#################################################################### +# +# If the platform is an ELKS box ... +# +#################################################################### +ifeq ($(ARCH), ELKS) + +# Higher speed asm driver, c driver of hercules screen driver +ASMVGADRIVER = Y +CVGADRIVER = N +HERCDRIVER = N +DBGDRIVER = N + +# Mouse support +SERMOUSE = Y + +endif diff --git a/packages/microwindows/files/makefilerules.patch b/packages/microwindows/files/makefilerules.patch new file mode 100644 index 0000000000..67b8e2e0d2 --- /dev/null +++ b/packages/microwindows/files/makefilerules.patch @@ -0,0 +1,14 @@ +--- microwindows-0.92/src/Makefile.rules-orig 2008-02-13 21:21:18.000000000 -0800 ++++ microwindows-0.92/src/Makefile.rules 2008-02-13 21:20:55.000000000 -0800 +@@ -569,9 +569,11 @@ + # If a shared object library name is specified, link this object + # + ifeq ($(SHAREDLIBS), Y) ++ifneq ($(LIBNAMESO),) + $(MW_DIR_LIB)/$(LIBNAMESO): $(MW_DIR_LIB)/$(LIBNAME) + @echo "Creating shared library $(patsubst $(MW_DIR_LIB)/%,%,$@) ..." + $(CC) -shared -o $@ -Wl,--whole-archive $^ -Wl,--no-whole-archive ++endif + endif + + # diff --git a/packages/microwindows/files/nochown.patch b/packages/microwindows/files/nochown.patch new file mode 100644 index 0000000000..7512c446a3 --- /dev/null +++ b/packages/microwindows/files/nochown.patch @@ -0,0 +1,17 @@ +--- microwindows-0.90/src/Makefile-orig.rules 2008-02-08 23:08:38.000000000 -0800 ++++ microwindows-0.90/src/Makefile.rules 2008-02-08 23:09:15.000000000 -0800 +@@ -23,10 +23,10 @@ + LIBINSTALLDIR = $(INSTALL_PREFIX)/lib + BININSTALLDIR = $(INSTALL_PREFIX)/bin + +-INSTALL_DIR = install -c -m 755 -o $(INSTALL_USER) -g $(INSTALL_GROUP) -d +-INSTALL_HDR = install -c -m 644 -o $(INSTALL_USER) -g $(INSTALL_GROUP_2) +-INSTALL_LIB = install -c -m 644 -o $(INSTALL_USER) -g $(INSTALL_GROUP_2) +-INSTALL_BIN = install -c -m 755 -o $(INSTALL_USER) -g $(INSTALL_GROUP_2) ++INSTALL_DIR = install -c -m 755 -d ++INSTALL_HDR = install -c -m 644 ++INSTALL_LIB = install -c -m 644 ++INSTALL_BIN = install -c -m 755 + + ############################################################################## + # Defines, includes, and core libraries. Controlled by the config file. diff --git a/packages/microwindows/files/pagesize.patch b/packages/microwindows/files/pagesize.patch new file mode 100644 index 0000000000..951ab27cce --- /dev/null +++ b/packages/microwindows/files/pagesize.patch @@ -0,0 +1,10 @@ +--- microwindows-0.90/src/nanox/clientfb-orig.c 2008-02-08 20:27:09.000000000 -0800 ++++ microwindows-0.90/src/nanox/clientfb.c 2008-02-08 20:24:49.000000000 -0800 +@@ -16,6 +16,7 @@ + #include "nano-X.h" + #include "lock.h" + ++#define PAGE_SIZE (1UL << 12) + #define CG6_RAM 0x70016000 /* for Sun systems*/ + + LOCK_EXTERN(nxGlobalLock); /* global lock for threads safety*/ diff --git a/packages/microwindows/files/staticwin.patch b/packages/microwindows/files/staticwin.patch new file mode 100644 index 0000000000..6d4ba2bb45 --- /dev/null +++ b/packages/microwindows/files/staticwin.patch @@ -0,0 +1,11 @@ +--- microwindows-0.91/src/demos/nanowm/wlist-orig.c 2001-11-15 14:49:18.000000000 -0800 ++++ microwindows-0.91/src/demos/nanowm/wlist.c 2008-02-12 09:56:59.000000000 -0800 +@@ -13,7 +13,7 @@ + + #include "nanowm.h" + +-static win *windows = NULL; ++win *windows = NULL; + + /* + * Find the windowlist entry for the specified window ID and return a pointer diff --git a/packages/microwindows/files/varargs.patch b/packages/microwindows/files/varargs.patch new file mode 100644 index 0000000000..1218e494cc --- /dev/null +++ b/packages/microwindows/files/varargs.patch @@ -0,0 +1,11 @@ +--- nxlib-0.45/Xlcint.h-orig 2008-02-13 20:46:56.000000000 -0800 ++++ nxlib-0.45/Xlcint.h 2008-02-13 20:47:16.000000000 -0800 +@@ -71,7 +71,7 @@ + #include "Xresource.h" + #include "Xutil.h" + /*#include "Xvarargs.h"*/ +-#include "varargs.h" ++#include "stdarg.h" + + typedef Bool (*XFilterEventProc)( + #if NeedFunctionPrototypes diff --git a/packages/microwindows/microwindows-snapshot.bb b/packages/microwindows/microwindows-snapshot.bb new file mode 100644 index 0000000000..e5f2314bb6 --- /dev/null +++ b/packages/microwindows/microwindows-snapshot.bb @@ -0,0 +1,10 @@ +require microwindows.inc + +SRC_URI = " \ + ftp://ftp.microwindows.org/pub/microwindows/microwindows-src-snapshot.tar.gz \ + file://defconfig \ + file://pagesize.patch;patch=1 \ + file://makefilerules.patch;patch=1 \ + " + +S=${WORKDIR}/microwin diff --git a/packages/microwindows/microwindows.inc b/packages/microwindows/microwindows.inc new file mode 100644 index 0000000000..6ddc141936 --- /dev/null +++ b/packages/microwindows/microwindows.inc @@ -0,0 +1,55 @@ +DESCRIPTION = "Microwindows Graphical Engine" +SECTION = "x11/wm" +PRIORITY = "optional" +DEPENDS = "libpng jpeg zlib" +LICENSE = "GPL" + +PR="r2" + +PARALLEL_MAKE = "" + +EXTRA_OEMAKE = " \ + -C ${S}/src \ + ARMTOOLSPREFIX=${TARGET_PREFIX} \ + INCJPEG=${STAGING_INCDIR} \ + LIBJPEG=${STAGING_LIBDIR}/libjpeg.so \ + INCPNG=${STAGING_INCDIR} \ + LIBPNG=${STAGING_LIBDIR}/libpng.so \ + LIBZ=${STAGING_LIBDIR}/libz.so \ + INSTALL_PREFIX=${D}${prefix} \ + INSTALL_OWNER1= \ + INSTALL_OWNER2= \ + " + +do_compile() { + cp ${WORKDIR}/defconfig ${S}/src/config + oe_runmake +} + +do_stage() { + install -m 0644 ${S}/src/include/nano-X.h ${STAGING_INCDIR}/ + install -m 0644 ${S}/src/include/mwtypes.h ${STAGING_INCDIR}/ + install -m 0644 ${S}/src/include/nxcolors.h ${STAGING_INCDIR}/ + install -m 0644 ${S}/src/include/nxdraw.h ${STAGING_INCDIR}/ + install -m 0755 ${S}/src/lib/*.so ${STAGING_LIBDIR}/ + install -m 0644 ${S}/src/lib/*.a ${STAGING_LIBDIR}/ +} + +do_install() { + oe_runmake install all + +# the next 3 lines are necessary for snapshot build since it has CVS cruft in the tarball + rm -rf ${S}/src/lib/CVS + rm -rf ${S}/src/bin/CVS + rm -f ${S}/src/bin/fonts + +# convbdf is a host tool - don't install it + mkdir ${S}/src/hostbin + mv ${S}/src/bin/convbdf ${S}/src/hostbin + + install -d ${D}${bindir} ${D}$bindir}/fonts ${D}${libdir} + install -m 0755 ${S}/src/lib/* ${D}${libdir}/ + install -m 0755 ${S}/src/bin/* ${D}${bindir}/ +} + +FILES_${PN}="${bindir}/* ${libdir}/*" diff --git a/packages/microwindows/microwindows_0.90.bb b/packages/microwindows/microwindows_0.90.bb index 495ab753d8..6fb76a92f1 100644 --- a/packages/microwindows/microwindows_0.90.bb +++ b/packages/microwindows/microwindows_0.90.bb @@ -1,41 +1,10 @@ -DESCRIPTION = "Microwindows Graphical Engine" -SECTION = "x11/wm" -PRIORITY = "optional" -DEPENDS = "libpng jpeg" -LICENSE = "GPL" -SRC_URI = "ftp://ftp.microwindows.org/pub/microwindows/microwindows-${PV}.tar.gz" +require microwindows.inc -export EXTRA_OEMAKE = "" +SRC_URI = " \ + ftp://ftp.microwindows.org/pub/microwindows/microwindows-${PV}.tar.gz \ + file://defconfig \ + file://pagesize.patch;patch=1 \ + file://nochown.patch;patch=1 \ + " -do_compile() { - if [ "${MACHINE}" = "ipaq" ]; then CONFIG=config.ipaq; fi - if [ "${MACHINE}" = "ads" ]; then CONFIG=config.ipaq; fi - if [ "${MACHINE}" = "tuxscreen" ]; then CONFIG=config.ipaq; fi - if [ "${MACHINE}" = "collie" ]; then CONFIG=config.zaurus; fi - if [ "${MACHINE}" = "collie" ]; then CONFIG=config.zaurus; fi - if [ -z "$CONFIG" ]; then CONFIG=config.fb; fi - cp src/Configs/$CONFIG src/config - - ARCH=`echo ${TARGET_OS}-${TARGET_ARCH} | tr [a-z] [A-Z]` - cd src - oe_runmake "ARCH=$ARCH" "TOOLSPREFIX=${TARGET_PREFIX}" "MICROWIN=N" \ - "MICROWINDEMO=N" "NANOWM=N" "SHAREDLIBS=Y" "DEBUG=N" \ - "INCJPEG=${STAGING_INCDIR}" "LIBJPEG=${STAGING_LIBDIR}/libjpeg.so" -} - -do_stage() { - install -m 0644 src/include/nano-X.h ${STAGING_INCDIR}/ - install -m 0644 src/include/mwtypes.h ${STAGING_INCDIR}/ - install -m 0644 src/include/nxcolors.h ${STAGING_INCDIR}/ - install -m 0644 src/include/nxdraw.h ${STAGING_INCDIR}/ - install -m 0755 src/lib/*.so ${STAGING_LIBDIR}/ - install -m 0644 src/lib/*.a ${STAGING_LIBDIR}/ -} - -do_install() { - install -d ${D}${bindir} ${D}${libdir} - install -m 0755 src/lib/*.so ${D}${libdir} - install -m 0755 src/bin/nano-X ${D}${bindir}/nano-X - #install -m 0755 src/bin/nxcal ${D}${bindir}/nxcal -} diff --git a/packages/microwindows/microwindows_0.91.bb b/packages/microwindows/microwindows_0.91.bb new file mode 100644 index 0000000000..4103ffad32 --- /dev/null +++ b/packages/microwindows/microwindows_0.91.bb @@ -0,0 +1,10 @@ +require microwindows.inc + +SRC_URI = " \ + ftp://ftp.microwindows.org/pub/microwindows/microwindows-src-${PV}.tar.gz \ + file://defconfig \ + file://pagesize.patch;patch=1 \ + file://staticwin.patch;patch=1 \ + " + + diff --git a/packages/microwindows/nxlib_0.45.bb b/packages/microwindows/nxlib_0.45.bb new file mode 100644 index 0000000000..a7a8d79fd9 --- /dev/null +++ b/packages/microwindows/nxlib_0.45.bb @@ -0,0 +1,24 @@ +DESCRIPTION = "NXLIB X11 Emulation Library for Nano-X" +PRIORITY = "optional" +LICENSE = "GPL" +PROVIDES = "virtual/libx11" +DEPENDS = "microwindows-snapshot" + +PR="r0" + +SRC_URI = " \ + ftp://ftp.microwindows.org/pub/microwindows/nxlib-${PV}.tar.gz \ + file://varargs.patch;patch=1 \ + " + +EXTRA_OEMAKE = ' \ + CC="${CC}" \ + MWIN=${STAGING_DIR}/${HOST_SYS} \ + X11=${STAGING_DIR}/${HOST_SYS} \ + ' + +# not sure yet about installation -- uncommenting below over-writes libX11 in staging +#do_install() { +# oe_runmake install +#} + diff --git a/packages/robostix-module/files/Makefile b/packages/robostix-module/files/Makefile new file mode 100644 index 0000000000..e242da4feb --- /dev/null +++ b/packages/robostix-module/files/Makefile @@ -0,0 +1,19 @@ +############################################################################# +# +# Makefile for building the robostix module +# +############################################################################# + +obj-m = robostix.o + +PWD = $(shell pwd) +KBUILD_FLAGS = -C $(KERNEL_PATH) M=$(PWD) KERNELRELEASE=$(KERNELRELEASE) + +default: modules + +modules: + $(MAKE) $(KBUILD_FLAGS) modules + +clean: + rm -rf *.o *~ *.ko *.mod.c + diff --git a/packages/robostix-module/files/robostix.c b/packages/robostix-module/files/robostix.c new file mode 100644 index 0000000000..1b3adac577 --- /dev/null +++ b/packages/robostix-module/files/robostix.c @@ -0,0 +1,1011 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* robostix.c +* +* PURPOSE: +* +* This implements a driver for using the robostix from the gumstix +* +* Initially, this contains the required support to emulate enough of the +* parallel port interface to allow avrdude to program the ATMega128. +* +*****************************************************************************/ + +/* ---- Include Files ---------------------------------------------------- */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include + +#include "robostix.h" + +/**************************************************************************** +* +* This driver assumes that the robostix uses the following GPIO pins: +* +* Robostix gumstix ATmega +* Symbol GPIO Dir Symbol Description +* ---------- ---- --- -------------- ------------------------------------- +* IR_RXD 46 in ATM_TX0 PE1 Acts as PDO or MISO for programming +* IR_TXD 47 out ATM_RX0 PE0 Acts as PDI or MOSI for programming +* +* L_DD11 69 in ATM_IRQ PE2 IRQ from ATmega128 to gumstix +* L_DD12 70 out Enable for Vcc5 and AVCC for the ATMega +* L_DD14 72 out Active low enable for the 245's +* L_DD15 73 out ATM_RESET Resets the processor +* +* The following shows the mapping of the SPI port for the gumstix: +* +* NSSPCLK 81 out ATM_SCK Acts as SCK for SPI use +* NSSPFRAME 82 out ATM_SS Acts as SS for SPI use +* X_MOSI 83 out ATM_MOSI Acts as MOSI for SPI use +* X_MISO 84 in ATM_MISO Acts as MISO for SPI use +* +* On the verdex, the mapping for the SPI port is slightly different: +* +* SSPCLK2 19 out ATM_SCK Acts as SCK for SPI use +* SSPSFRM2 14 out ATM_SS Acts as SS for SPI use +* SSPTXD2 13 out ATM_MOSI Acts as MOSI for SPI use +* SSPRXD2 11 in ATM_MISO Acts as MISO for SPI use +* +* X_SCL - i/o ATM_SCL i2c clock +* X_SDA - i/o ATM_SDA i2c data +* +*****************************************************************************/ + +//--------------------------------------------------------------------------- +// +// This was extracted from avrdude, and it gives the pin configuration for +// AVR Dude's default programmer. UISP calls it "BSD" +// This is what I've chosen for this driver to implement. + +#if 0 +programmer + id = "bsd"; + desc = "Brian Dean's Programmer, http://www.bsdhome.com/avrdude/"; + type = par; + vcc = 2, 3, 4, 5; + reset = 7; + sck = 8; + mosi = 9; + miso = 10; +; +#endif +//--------------------------------------------------------------------------- +// +// The following was extracted from avrdude. It basically gives the pin +// number to register mapping that is in effect for the parallel port. +// +// I added the comments on the right which shows pin usage for the default +// programmer. +// +// From this, we can glean that the Control register is never used, and none +// of the signals which are used are inverted. +// +// Furthermore, all of the Data accesses are writes and all of the Status +// accesses are reads. + +#if 0 +struct ppipins_t { + int pin; + int reg; + int bit; + int inverted; +}; + +static struct ppipins_t pins[] = { + { 1, PPICTRL, 0x01, 1 }, + { 2, PPIDATA, 0x01, 0 }, // Vcc + { 3, PPIDATA, 0x02, 0 }, // Vcc + { 4, PPIDATA, 0x04, 0 }, // Vcc + { 5, PPIDATA, 0x08, 0 }, // Vcc + { 6, PPIDATA, 0x10, 0 }, + { 7, PPIDATA, 0x20, 0 }, // Reset + { 8, PPIDATA, 0x40, 0 }, // SCK + { 9, PPIDATA, 0x80, 0 }, // MOSI + { 10, PPISTATUS, 0x40, 0 }, // MISO + { 11, PPISTATUS, 0x80, 1 }, + { 12, PPISTATUS, 0x20, 0 }, + { 13, PPISTATUS, 0x10, 0 }, + { 14, PPICTRL, 0x02, 1 }, + { 15, PPISTATUS, 0x08, 0 }, + { 16, PPICTRL, 0x04, 0 }, + { 17, PPICTRL, 0x08, 1 } +}; + +#endif + +#define PPI_DATA_VCC_MASK ( 0x01 | 0x02 | 0x04 | 0x08 ) +#define PPI_DATA_RESET_MASK ( 0x20 ) +#define PPI_DATA_SCK_MASK ( 0x40 ) +#define PPI_DATA_MOSI_MASK ( 0x80 ) + +#define PPI_STATUS_MISO_MASK ( 0x40 ) + +/* ---- Public Variables ------------------------------------------------- */ +/* ---- Private Constants and Types -------------------------------------- */ + +#define USE_SYSCTL 1 + +#if 1 +# if USE_SYSCTL +# define ROBO_DEBUG( flag, fmt, args... ) do { if ( gDebug ## flag ) printk( "%s: " fmt, __FUNCTION__ , ## args ); } while (0) +# else +# define ROBO_DEBUG( flag, fmt, args... ) printk( "%s: " fmt, __FUNCTION__ , ## args ) +# endif +#else +# define ROBO_DEBUG( flag, fmt, args... ) +#endif + +#define SET_GPIO( pin, val ) do { if ( val ) { GPSR( pin ) = GPIO_bit( pin ); } else { GPCR( pin ) = GPIO_bit( pin ); }} while(0) +#define GET_GPIO( pin ) (( GPLR( pin ) & GPIO_bit( pin )) != 0 ) + +// The Alternate function register is 2 bits per pin, so we can't use the +// GPIO_bit macro. + +#define GPIO_AF_shift(x) (((x) & 0x0F ) << 1 ) +#define GPIO_AF_mask(x) ( 3 << GPIO_AF_shift( x )) + +/* + * Define the mappings between various GPIO pins and functions on the robostix + * board. + */ + +#define ROBOSTIX_GPIO_ATM_IRQ GPIO69_LDD_11 +#define ROBOSTIX_GPIO_VCC5_ENABLE GPIO70_LDD_12 +#define ROBOSTIX_GPIO_245_ENABLE GPIO72_LDD_14 +#define ROBOSTIX_GPIO_ATM_RESET GPIO73_LDD_15 + +#ifdef CONFIG_PXA27x +# define ROBOSTIX_GPIO_ATM_SCK ( 19 | GPIO_ALT_FN_1_OUT ) +# define ROBOSTIX_GPIO_ATM_SS ( 14 | GPIO_ALT_FN_2_OUT ) +# define ROBOSTIX_GPIO_ATM_MOSI ( 13 | GPIO_ALT_FN_1_OUT ) +# define ROBOSTIX_GPIO_ATM_MISO ( 11 | GPIO_ALT_FN_2_IN ) +#else +# define ROBOSTIX_GPIO_ATM_SCK GPIO81_NSCLK +# define ROBOSTIX_GPIO_ATM_SS GPIO82_NSFRM +# define ROBOSTIX_GPIO_ATM_MOSI GPIO83_NSTXD +# define ROBOSTIX_GPIO_ATM_MISO GPIO84_NSRXD +#endif + +#define ROBOSTIX_GPIO_IR_RXD_5V GPIO46_STRXD +#define ROBOSTIX_GPIO_IR_TXD_5V GPIO47_STTXD + +// Since IR TxD/RxD behave like MOSI/MISO during programming, we define a +// couple of aliases + +#define ROBOSTIX_GPIO_ATM_PGM_MOSI ROBOSTIX_GPIO_IR_TXD_5V +#define ROBOSTIX_GPIO_ATM_PGM_MISO ROBOSTIX_GPIO_IR_RXD_5V + + +typedef enum +{ + RoboStixGpioIn, + RoboStixGpioOut, +} PinMode_e; + +typedef struct +{ + unsigned grer; + unsigned gfer; + unsigned gafr; + unsigned gpdr; + unsigned gplr; + +} PinConfig_t; + +/* ---- Private Variables ------------------------------------------------ */ + +#define ROBOSTIX_DEV_NAME "robostix" + +static char gBanner[] __initdata = KERN_INFO "Robostix Driver Compiled: " __DATE__ " at " __TIME__ "\n"; + +static PinConfig_t gIrTxdConfig; +static PinConfig_t gIrRxdConfig; + +dev_t gRobostixDevNum; +struct cdev gRobostixCDev; +struct class *gRobostixClass; + +#if USE_SYSCTL + +static int gDebugTrace = 0; +static int gDebugIoctl = 0; +static int gDebugError = 1; + +static struct ctl_table_header *gSysCtlHeader; + +static struct ctl_table gSysCtlRobostix[] = +{ + { + .ctl_name = CTL_ROBOSTIX_DEBUG_TRACE, + .procname = "debug-trace", + .data = &gDebugTrace, + .maxlen = sizeof( int ), + .mode = 0644, + .proc_handler = &proc_dointvec + }, + { + .ctl_name = CTL_ROBOSTIX_DEBUG_IOCTL, + .procname = "debug-ioctl", + .data = &gDebugIoctl, + .maxlen = sizeof( int ), + .mode = 0644, + .proc_handler = &proc_dointvec + }, + { + .ctl_name = CTL_ROBOSTIX_DEBUG_ERROR, + .procname = "debug-error", + .data = &gDebugError, + .maxlen = sizeof( int ), + .mode = 0644, + .proc_handler = &proc_dointvec + }, + { 0 } +}; + +static struct ctl_table gSysCtl[] = +{ + { + .ctl_name = CTL_ROBOSTIX, + .procname = "robostix", + .mode = 0555, + .child = gSysCtlRobostix + }, + { 0 } +}; + +#endif // USE_SYSCTL + +/* ---- Private Function Prototypes -------------------------------------- */ + +static void robostix_configure_pin( int pin, PinMode_e pinMode ); +static void robostix_get_pin_config( int pin, PinConfig_t *pinConfig ); +static void robostix_set_pin_config( int pin, const PinConfig_t *pinConfig ); + +static void robostix_exit( void ); +static int robostix_init( void ); +static int robostix_ioctl( struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg ); +static int robostix_open( struct inode *inode, struct file *file ); +static int robostix_release( struct inode *inode, struct file *file ); + +/**************************************************************************** +* +* File Operations (these are the device driver entry points) +* +*****************************************************************************/ + +static struct file_operations robostix_fops = +{ + owner: THIS_MODULE, + ioctl: robostix_ioctl, + open: robostix_open, + release: robostix_release, +}; + +/* ---- Functions -------------------------------------------------------- */ + +/**************************************************************************** +* +* robostix_configure_pin +* +* Configures a GPIO pin for use with the RoboStix. +* +*****************************************************************************/ + +void robostix_configure_pin( int pin, PinMode_e pinMode ) +{ + // Make sure that interrupts on rising/falling edges are turned off. This + // is a bit paranoid, but might as well be sure. + + GRER( pin ) &= ~GPIO_bit( pin ); + GFER( pin ) &= ~GPIO_bit( pin ); + + // Set the pin to be a GPIO pin + + GAFR( pin ) &= ~GPIO_AF_mask( pin ); // AF = 0 is GPIO + + // Reprogram the direction of the pin. + + if ( pinMode == RoboStixGpioIn ) + { + GPDR( pin ) &= ~GPIO_bit( pin ); // in + } + else + { + GPDR( pin ) |= GPIO_bit( pin ); // out + } + +} // robostix_configure_pin + +/**************************************************************************** +* +* robostix_get_pin_config +* +* Retrieves the current pin configuration and stores it in @a pinConfig. +* +*****************************************************************************/ + +void robostix_get_pin_config( int pin, PinConfig_t *pinConfig ) +{ + pinConfig->grer = GRER( pin ) & GPIO_bit( pin ); + pinConfig->gfer = GFER( pin ) & GPIO_bit( pin ); + pinConfig->gafr = GAFR( pin ) & GPIO_AF_mask( pin ); + pinConfig->gpdr = GPDR( pin ) & GPIO_bit( pin ); + pinConfig->gplr = GPLR( pin ) & GPIO_bit( pin ); + +} // robostix_get_pin_config + +/**************************************************************************** +* +* robostix_set_pin_config +* +* Restores the pin configuration to a previously saved comfiguration. +* +*****************************************************************************/ + +void robostix_set_pin_config( int pin, const PinConfig_t *pinConfig ) +{ + GRER( pin ) = ( GRER( pin ) & ~GPIO_bit( pin )) | ( pinConfig->grer & GPIO_bit( pin )); + GFER( pin ) = ( GFER( pin ) & ~GPIO_bit( pin )) | ( pinConfig->gfer & GPIO_bit( pin )); + GPDR( pin ) = ( GPDR( pin ) & ~GPIO_bit( pin )) | ( pinConfig->gpdr & GPIO_bit( pin )); + GAFR( pin ) = ( GAFR( pin ) & ~GPIO_AF_mask( pin )) | ( pinConfig->gafr & GPIO_AF_mask( pin )); + + if (( pinConfig->gplr & GPIO_bit( pin )) == 0 ) + { + GPSR( pin ) |= GPIO_bit( pin ); + } + else + { + GPCR( pin ) |= GPIO_bit( pin ); + } + +} // robostix_set_pin_config + +/**************************************************************************** +* +* robostix_exit +* +* Called to perform module cleanup when the module is unloaded. +* +*****************************************************************************/ + +void robostix_exit( void ) +{ + ROBO_DEBUG( Trace, "called\n" ); + + class_device_destroy( gRobostixClass, gRobostixDevNum ); + class_destroy( gRobostixClass ); + + cdev_del( &gRobostixCDev ); + +#if USE_SYSCTL + if ( gSysCtlHeader != NULL ) + { + unregister_sysctl_table( gSysCtlHeader ); + } +#endif + + unregister_chrdev_region( gRobostixDevNum, 1 ); + +#if 0 + unregister_chrdev( ROBOSTIX_MAJOR, ROBOSTIX_DEV_NAME ); +#endif + +} // robostix_exit + +/**************************************************************************** +* +* robostix_init +* +* Called to perform module initialization when the module is loaded. +* +*****************************************************************************/ + +int __init robostix_init( void ) +{ + int rc; + + ROBO_DEBUG( Trace, "called\n" ); + + printk( gBanner); + +#if 0 + // Register our device with Linux + + if (( rc = register_chrdev( ROBOSTIX_MAJOR, ROBOSTIX_DEV_NAME, &robostix_fops )) < 0 ) + { + printk( KERN_WARNING "robostix: register_chrdev failed for major %d\n", ROBOSTIX_MAJOR ); + return rc; + } +#endif + + if (( rc = alloc_chrdev_region( &gRobostixDevNum, 0, 1, ROBOSTIX_DEV_NAME )) < 0 ) + { + printk( KERN_WARNING "robostix: Unable to allocate major, err: %d\n", rc ); + return rc; + } + +#if USE_SYSCTL + #if ( LINUX_VERSION_CODE <= KERNEL_VERSION( 2, 6, 20 )) + gSysCtlHeader = register_sysctl_table( gSysCtl, 0 ); + if ( gSysCtlHeader != NULL ) + { + gSysCtlHeader->ctl_table->child->de->owner = THIS_MODULE; + } + #else + gSysCtlHeader = register_sysctl_table( gSysCtl ); + #endif +#endif + + // Initialize the various GPIO pins that control the Robostix. + // + // IR_RXD 46 in ATM_TX0 PE1 Acts as PDO or MISO for programming + // IR_TXD 47 out ATM_RX0 PE0 Acts as PDI or MOSI for programming + // + // L_DD11 69 in ATM_IRQ PE2 IRQ from ATmega128 to gumstix + // L_DD12 70 out Enable for Vcc5 and AVCC for the ATMega + // L_DD14 72 out Active low enable for the 245's + // L_DD15 73 out ATM_RESET Resets the processor + // + // NSSPCLK 81 out ATM_SCK Acts as SCK for SPI use + // NSSPFRAME 82 out ATM_SS Acts as SS for SPI use + // X_MOSI 83 out ATM_MOSI Acts as MOSI for SPI use + // X_MISO 84 in ATM_MISO Acts as MISO for SPI use + // + // For now, we initialize things so that they continue on the way that + // they were when the gumstix boots: + // + // 245 is enabled + // voltage regulators are enabled + // Robostix is held in Reset + // + // I'd like to either see the voltage regulators in a disabled state + // or see the robostix not be held in reset so that we don't have sensors + // and motors and stuff going wild while the gumstix boots. + // + // The gumstix console runs through the '245 so we make sure to leave + // it enabled. + + // The first thing to do is configure the input pins. + + robostix_configure_pin( ROBOSTIX_GPIO_ATM_MISO, RoboStixGpioIn ); + + // TODO: Set ATM_IRQ line to generate an interrupt + +// printk( "IRQ\n" ); +// robostix_configure_pin( ROBOSTIX_GPIO_ATM_IRQ, RoboStixGpioIn ); + + // Configure the output pins. We set the GPIO value register before + // setting configuring it as a GPIO so that we don't create a glitch. + + SET_GPIO( ROBOSTIX_GPIO_VCC5_ENABLE, 1 ); // Voltage regulator on (active high) + robostix_configure_pin( ROBOSTIX_GPIO_VCC5_ENABLE, RoboStixGpioOut ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, 0 ); // AVR held in Reset (active low) + robostix_configure_pin( ROBOSTIX_GPIO_ATM_RESET, RoboStixGpioOut ); + + // The values of these pins don't really matter. + + robostix_configure_pin( ROBOSTIX_GPIO_ATM_SCK, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_ATM_SS, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_ATM_MOSI, RoboStixGpioOut ); + + // Finally enable the '245 + + SET_GPIO( ROBOSTIX_GPIO_245_ENABLE, 0 ); // '245 enabled (active low) + robostix_configure_pin( ROBOSTIX_GPIO_245_ENABLE, RoboStixGpioOut ); + + // Don't change the configuration of the IR TxD/RxD here. Instead we + // save/restore using the PPCLAIM/PPRELEASE which brackets when avrdude + // is doing the actual programming. + + // TODO: Probably configure IR TxD as UART + + // Register our device. The device becomes "active" as soon as cdev_add + // is called. + + cdev_init( &gRobostixCDev, &robostix_fops ); + gRobostixCDev.owner = THIS_MODULE; + + if (( rc = cdev_add( &gRobostixCDev, gRobostixDevNum, 1 )) != 0 ) + { + printk( KERN_WARNING "robostix: cdev_add failed: %d\n", rc ); + return rc; + } + + gRobostixClass = class_create( THIS_MODULE, ROBOSTIX_DEV_NAME ); + if ( IS_ERR( gRobostixClass )) + { + printk( KERN_WARNING "robostix: Unable to create class\n" ); + return -1; + } + + class_device_create( gRobostixClass, NULL, gRobostixDevNum, NULL, ROBOSTIX_DEV_NAME ); + + return 0; + +} // robostix_init + +/**************************************************************************** +* +* robostix_ioctl +* +* Called to process ioctl requests +* +*****************************************************************************/ + +int robostix_ioctl( struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg ) +{ + int err; + int userVal; + + ROBO_DEBUG( Trace, "type: '%c' cmd: 0x%x\n", _IOC_TYPE( cmd ), _IOC_NR( cmd )); + + if (( _IOC_TYPE( cmd ) != ROBOSTIX_IOCTL_MAGIC ) + || ( _IOC_NR( cmd ) < ROBOSTIX_CMD_FIRST ) + || ( _IOC_NR( cmd ) >= ROBOSTIX_CMD_LAST )) + { + // Since we emulate some of the parallel port commands, we need to allow + // those as well. + + if (( _IOC_TYPE( cmd ) != PP_IOCTL ) + || ( _IOC_NR( cmd ) < 0x80 ) + || ( _IOC_NR( cmd ) >= 0x9b )) + { + return -ENOTTY; + } + } + + // Note that _IOC_DIR Read/Write is from the perspective of userland. access_ok + // is from the perspective of kernelland. + + err = 0; + if (( _IOC_DIR( cmd ) & _IOC_READ ) != 0 ) + { + err |= !access_ok( VERIFY_WRITE, (void *)arg, _IOC_SIZE( cmd )); + } + if (( _IOC_DIR( cmd ) & _IOC_WRITE ) != 0 ) + { + err |= !access_ok( VERIFY_READ, (void *)arg, _IOC_SIZE( cmd )); + } + if ( err ) + { + ROBO_DEBUG( Error, "arg pointer is invalid\n" ); + return -EFAULT; + } + + switch ( cmd ) + { + case ROBOSTIX_IOCTL_POWER_VCC5: + { + ROBO_DEBUG( Ioctl, "Power: %ld\n", arg ); + +#if 1 + // Until I figure something else out, the only way I can get the + // power to really go off is to also turn off the '245. This means + // that we'll lose the console, so you better be turning things + // back on real soon now + + SET_GPIO( ROBOSTIX_GPIO_245_ENABLE, !arg ); // '245 is active low + + // Also - I noticed that the Console connector on the Robostix has + // Vcc5 going to it, which means that if a TTL <=> RS232 converter + // is being powered off the robostix, we'll lose our console as + // soon as the voltage regulator (which generates Vcc5) gets + // turned off. + +#else + // In order to truly power off the robostix, we need to turn off + // the voltage regulator. We assume that the '245 stays on so we + // continue to get our console. This also means that we need to + // take all of the GPIO lines low to eliminate any leak-thru + // current. + + if ( arg ) + { + // Powering on - Configure I/O pins in "typical" manner. + + // TODO: Probably set MOSI/SCK/SS back to NSSP + // TODO: Probably set IR TxD back to UART + } + else + { + // Powering off. Make them all GPIO's so that we can force + // them low. + + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, 0 ); + SET_GPIO( ROBOSTIX_GPIO_ATM_MOSI, 0 ); + SET_GPIO( ROBOSTIX_GPIO_ATM_SCK, 0 ); + SET_GPIO( ROBOSTIX_GPIO_ATM_SS, 0 ); + SET_GPIO( ROBOSTIX_GPIO_IR_TXD_5V, 0 ); + + robostix_configure_pin( ROBOSTIX_GPIO_ATM_RESET, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_ATM_MOSI, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_ATM_SCK, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_ATM_SS, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_IR_TXD_5V, RoboStixGpioOut ); + + // Grr - ATM_SCL and ATM_SDA are both pulled up to V_BATT, + // so we probably need to make these go low too, which effectively + // means that we lose the i2c bus. + } +#endif + + SET_GPIO( ROBOSTIX_GPIO_VCC5_ENABLE, arg ); // Voltage regulator is active high + break; + } + + case ROBOSTIX_IOCTL_RESET: + { + if ( arg == ROBOSTIX_PIN_PULSE ) + { + // The ATMega128 datasheet says that the reset pulse needs + // to have a minimum pulse width of 1.5 usec. + + ROBO_DEBUG( Ioctl, "Reset: %ld (pulse)\n", arg ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, 0 ); // Reset is active low + udelay( 3 ); + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, 1 ); + } + else + { + // Reset is active low, so "on" means low + + ROBO_DEBUG( Ioctl, "Reset: %ld\n", arg ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, !arg ); + } + break; + } + + case ROBOSTIX_IOCTL_245_ENABLE: + { + // The 245 is active low, so we invert the sense of on/off + + ROBO_DEBUG( Ioctl, "245 Enable: %ld\n", arg ); + + if ( arg != 0 ) + { + printk( KERN_WARNING "Robostix: Warning turning '245 off - console may become inactive\n" ); + + // Allow some time for the above warning to get printed on the + // console before we turn it off. + + set_current_state( TASK_INTERRUPTIBLE ); + schedule_timeout( 2 ); + } + + SET_GPIO( ROBOSTIX_GPIO_245_ENABLE, !arg ); + break; + } + + case ROBOSTIX_IOCTL_SET_SCK: // out + { + ROBO_DEBUG( Ioctl, "Set SCK: %ld\n", arg ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_SCK, arg ); + break; + } + + case ROBOSTIX_IOCTL_SET_SS: // out + { + ROBO_DEBUG( Ioctl, "Set SS: %ld\n", arg ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_SS, arg ); + break; + } + + case ROBOSTIX_IOCTL_SET_IR_TXD: // out + { + // This particular ioctl should only ever be called as part of + // somebody testing something. We assume that they'll be smart + // enough to reconfigure when they're done. + + ROBO_DEBUG( Ioctl, "Set IR TxD: %ld\n", arg ); + + robostix_configure_pin( ROBOSTIX_GPIO_IR_TXD_5V, RoboStixGpioOut ); + + SET_GPIO( ROBOSTIX_GPIO_IR_TXD_5V, arg ); + break; + } + + case ROBOSTIX_IOCTL_GET_IR_RXD: // in + { + // This particular ioctl should only ever be called as part of + // somebody testing something. We assume that they'll be smart + // enough to reconfigure when they're done. + + robostix_configure_pin( ROBOSTIX_GPIO_IR_RXD_5V, RoboStixGpioIn ); + + userVal = GET_GPIO( ROBOSTIX_GPIO_IR_RXD_5V ); + if ( copy_to_user( (int *)arg, &userVal, sizeof( userVal )) != 0 ) + { + return -EFAULT; + } + + ROBO_DEBUG( Ioctl, "Get IR RxD: %d\n", userVal ); + break; + } + + case ROBOSTIX_IOCTL_SET_MOSI: // out + { + ROBO_DEBUG( Ioctl, "Set MOSI: %ld\n", arg ); + + SET_GPIO( ROBOSTIX_GPIO_ATM_MOSI, arg ); + break; + } + + case ROBOSTIX_IOCTL_GET_MISO: // in + { + userVal = GET_GPIO( ROBOSTIX_GPIO_ATM_MISO ); + if ( copy_to_user( (int *)arg, &userVal, sizeof( userVal )) != 0 ) + { + return -EFAULT; + } + ROBO_DEBUG( Ioctl, "Get MISO: %d\n", userVal ); + break; + } + + case ROBOSTIX_IOCTL_GET_IRQ: // in + { + userVal = GET_GPIO( ROBOSTIX_GPIO_ATM_IRQ ); + if ( copy_to_user( (int *)arg, &userVal, sizeof( userVal )) != 0 ) + { + return -EFAULT; + } + ROBO_DEBUG( Ioctl, "Get IRQ: %d\n", userVal ); + break; + } + + case ROBOSTIX_IOCTL_DELAY_USEC: + { + ROBO_DEBUG( Ioctl, "Delay: %ld usecs\n", arg ); + + udelay( arg ); + break; + } + + //------------------------------------------------------------------- + // + // Parallel port interface. Some documentation on these ioctls can + // be found here: + // http://www.kernelnewbies.org/documents/kdoc/parportbook/x623.html + // + + case PPRSTATUS: // Read status register + { + unsigned char statusReg = 0; + int miso; + + // The only thing mapped into the status register, is MISO. + + miso = GET_GPIO( ROBOSTIX_GPIO_ATM_PGM_MISO ); + + + if ( miso ) + { + statusReg |= PPI_STATUS_MISO_MASK; + } + + ROBO_DEBUG( Ioctl, "PPRSTATUS: 0x%02x miso:%d\n", statusReg, miso ); + + if ( copy_to_user( (unsigned char *)arg, &statusReg, sizeof( statusReg )) != 0 ) + { + return -EFAULT; + } + break; + } + + case PPRCONTROL: // Read control register + { + // Called once to initialize avrdude's shadow registers + + unsigned char controlReg = 0; + + ROBO_DEBUG( Ioctl, "PPRCONTROL: 0x%02x\n", controlReg ); + + if ( copy_to_user( (unsigned char *)arg, &controlReg, sizeof( controlReg )) != 0 ) + { + return -EFAULT; + } + break; + } + + case PPWCONTROL: // Write control register + { + unsigned char controlReg = 0; + + if ( copy_from_user( &controlReg, (unsigned char *)arg, sizeof( controlReg )) != 0 ) + { + return -EFAULT; + } + + ROBO_DEBUG( Ioctl, "PPWCONTROL: 0x%02x\n", controlReg ); + break; + } + + case PPRDATA: // Read data register + { + // Called once to initialize avrdude's shadow registers + + unsigned char dataReg = 0; + int power, sck, reset, mosi; + + power = GET_GPIO( ROBOSTIX_GPIO_VCC5_ENABLE ); + sck = GET_GPIO( ROBOSTIX_GPIO_ATM_SCK ); + reset = GET_GPIO( ROBOSTIX_GPIO_ATM_RESET ); + mosi = GET_GPIO( ROBOSTIX_GPIO_ATM_PGM_MOSI ); + + if ( power ) + { + dataReg |= PPI_DATA_VCC_MASK; + } + if ( reset ) + { + dataReg |= PPI_DATA_RESET_MASK; + } + if ( sck ) + { + dataReg |= PPI_DATA_SCK_MASK; + } + if ( mosi ) + { + dataReg |= PPI_DATA_MOSI_MASK; + } + + ROBO_DEBUG( Ioctl, "PPRDATA: 0x%02x pow:%d reset:%d sck:%d mosi: %d\n", dataReg, power, reset, sck, mosi ); + + if ( copy_to_user( (unsigned char *)arg, &dataReg, sizeof( dataReg )) != 0 ) + { + return -EFAULT; + } + break; + } + + case PPWDATA: // Write data register + { + unsigned char dataReg = 0; + int power, sck, reset, mosi; + + if ( copy_from_user( &dataReg, (unsigned char *)arg, sizeof( dataReg )) != 0 ) + { + return -EFAULT; + } + + power = ( dataReg & PPI_DATA_VCC_MASK ) != 0; + sck = ( dataReg & PPI_DATA_SCK_MASK ) != 0; + reset = ( dataReg & PPI_DATA_RESET_MASK ) != 0; + mosi = ( dataReg & PPI_DATA_MOSI_MASK ) != 0; + + ROBO_DEBUG( Ioctl, "PPWDATA: 0x%02x pow:%d reset:%d sck:%d mosi: %d\n", dataReg, power, reset, sck, mosi ); + + SET_GPIO( ROBOSTIX_GPIO_VCC5_ENABLE, power ); + SET_GPIO( ROBOSTIX_GPIO_245_ENABLE, !power ); // 245 is active low + + SET_GPIO( ROBOSTIX_GPIO_ATM_SCK, sck ); + SET_GPIO( ROBOSTIX_GPIO_ATM_RESET, reset ); + SET_GPIO( ROBOSTIX_GPIO_ATM_PGM_MOSI, mosi ); + break; + } + + case PPCLAIM: // Claim the parallel port + { + ROBO_DEBUG( Ioctl, "PPCLAIM\n" ); + + // We use this opportunity to save away the state of the IR Txd/Rxd lines + // and convert them to GPIO. + + robostix_get_pin_config( ROBOSTIX_GPIO_IR_TXD_5V, &gIrTxdConfig ); + robostix_get_pin_config( ROBOSTIX_GPIO_IR_RXD_5V, &gIrRxdConfig ); + + robostix_configure_pin( ROBOSTIX_GPIO_IR_TXD_5V, RoboStixGpioOut ); + robostix_configure_pin( ROBOSTIX_GPIO_IR_RXD_5V, RoboStixGpioIn ); + break; + } + + case PPRELEASE: // Release the parallel port + { + ROBO_DEBUG( Ioctl, "PPRELEASE\n" ); + + // We use this opportunity to restore the state of the IR Txd/Rxd lines + // back to what they were. + + robostix_set_pin_config( ROBOSTIX_GPIO_IR_TXD_5V, &gIrTxdConfig ); + robostix_set_pin_config( ROBOSTIX_GPIO_IR_RXD_5V, &gIrRxdConfig ); + break; + } + + case PPDATADIR: + { + int dataDirReg; + + if ( copy_from_user( &dataDirReg, (int *)arg, sizeof( dataDirReg )) != 0 ) + { + return -EFAULT; + } + + ROBO_DEBUG( Ioctl, "PPDATADIR: 0x%02x\n", dataDirReg ); + break; + } + + default: + { + ROBO_DEBUG( Error, "Unrecognized ioctl: '0x%x'\n", cmd ); + return -ENOTTY; + } + } + + return 0; + +} // robostix_ioctl + +/**************************************************************************** +* +* robostix_open +* +* Called to process open requests +* +*****************************************************************************/ + +int robostix_open( struct inode *inode, struct file *file ) +{ + ROBO_DEBUG( Trace, "major = %d, minor = %d\n", MAJOR( inode->i_rdev ), MINOR( inode->i_rdev )); + + return 0; + +} // robostix_open + +/**************************************************************************** +* +* robostix_release +* +* Called when the last istance is closed. +* +*****************************************************************************/ + +int robostix_release( struct inode *inode, struct file *file ) +{ + ROBO_DEBUG( Trace, "called\n" ); + + return 0; + +} // robostix_release + +/****************************************************************************/ + +module_init(robostix_init); +module_exit(robostix_exit); + +MODULE_AUTHOR("Dave Hylands"); +MODULE_DESCRIPTION("gumstix/robostix driver"); +MODULE_LICENSE("Dual BSD/GPL"); + diff --git a/packages/robostix-module/files/robostix.h b/packages/robostix-module/files/robostix.h new file mode 100644 index 0000000000..0d860bc7a4 --- /dev/null +++ b/packages/robostix-module/files/robostix.h @@ -0,0 +1,114 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* robostix_drv.h +* +* PURPOSE: +* +* This implements a driver for using the robostix from the gumstix +* +* Initially, this contains the required support to emulate enough of the +* parallel port interface to allow avrdude to program the ATMega128. +* +*****************************************************************************/ + +#if !defined( LINUX_ROBOSTIX_H ) +#define LINUX_ROBOSTIX_H ) + +/* ---- Include Files ----------------------------------------------------- */ + +#include + +/* ---- Constants and Types ----------------------------------------------- */ + +#define ROBOSTIX_MAJOR 240 + +#define ROBOSTIX_IOCTL_MAGIC 'R' + +/** + * Deefines for each of the commands. Note that since we want to reduce + * the possibility that a user mode program gets out of sync with a given + * driver, we explicitly assign a value to each enumeration. This makes + * it more difficult to stick new ioctl's in the middle of the list. + */ + +typedef enum +{ + ROBOSTIX_CMD_FIRST = 0x80, + + ROBOSTIX_CMD_POWER_VCC5 = 0x80, + ROBOSTIX_CMD_RESET = 0x81, + ROBOSTIX_CMD_245_ENABLE = 0x82, + ROBOSTIX_CMD_SET_SCK = 0x83, + ROBOSTIX_CMD_SET_SS = 0x84, + ROBOSTIX_CMD_SET_IR_TXD = 0x85, + ROBOSTIX_CMD_GET_IR_RXD = 0x86, + ROBOSTIX_CMD_SET_MOSI = 0x87, + ROBOSTIX_CMD_GET_MISO = 0x88, + ROBOSTIX_CMD_GET_IRQ = 0x89, + ROBOSTIX_CMD_DELAY_USEC = 0x8A, // value is hardocded in uisp DAPA.C + + /* Insert new ioctls here */ + + ROBOSTIX_CMD_LAST, + +} ROBOSTIX_CMD; + +/* + * The following are arguments to the various ioctl's + */ + +#define ROBOSTIX_PIN_OFF 0 +#define ROBOSTIX_PIN_ON 1 +#define ROBOSTIX_PIN_PULSE 2 // only used or Reset + +/* + * Definitions for the actual ioctl commands + */ + +#define ROBOSTIX_IOCTL_POWER_VCC5 _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_POWER_VCC5 ) // arg is int +#define ROBOSTIX_IOCTL_RESET _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_RESET ) // arg is int +#define ROBOSTIX_IOCTL_245_ENABLE _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_245_ENABLE ) // arg is int +#define ROBOSTIX_IOCTL_SET_SCK _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_SCK ) // arg is int +#define ROBOSTIX_IOCTL_SET_SS _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_SS ) // arg is int +#define ROBOSTIX_IOCTL_SET_IR_TXD _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_IR_TXD ) // arg is int +#define ROBOSTIX_IOCTL_GET_IR_RXD _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_IR_RXD, int ) // arg is int * +#define ROBOSTIX_IOCTL_SET_MOSI _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_MOSI ) // arg is int +#define ROBOSTIX_IOCTL_GET_MISO _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_MISO, int ) // arg is int * +#define ROBOSTIX_IOCTL_GET_IRQ _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_IRQ, int ) // arg is int * +#define ROBOSTIX_IOCTL_DELAY_USEC _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_DELAY_USEC ) // arg is int + + +/* + * Definitions for sysctl. The top level define has to be unique system wide. + * The kernel defines values 1 thru about 10 (see include/linunx/sysctl.h) + */ + +#define CTL_ROBOSTIX 0x526F626F /* 'Robo' in hex form */ + +/* + * The following are for entries in /proc/sys/robostix + */ + +enum +{ + CTL_ROBOSTIX_DEBUG_TRACE = 101, + CTL_ROBOSTIX_DEBUG_IOCTL = 102, + CTL_ROBOSTIX_DEBUG_ERROR = 103 +}; + +#endif // LINUX_ROBOSTIX_H + diff --git a/packages/robostix-module/files/robostix.init b/packages/robostix-module/files/robostix.init new file mode 100755 index 0000000000..9bbd1d9e7c --- /dev/null +++ b/packages/robostix-module/files/robostix.init @@ -0,0 +1,53 @@ +#!/bin/sh +# +# Start the robostix +# + +start() { + echo "Starting robostix..." + + # Make sure ttyS2 is setup + echo "AF2 in" > /proc/gpio/GPIO46 + echo "AF1 out" > /proc/gpio/GPIO47 + + # Turn on the robostix '245 + echo "GPIO out clear" > /proc/gpio/GPIO72 + + # Turn on the robostix Power + echo "GPIO out set" > /proc/gpio/GPIO70 + + # load driver + /sbin/modprobe robostix + + # Take the robostix out of reset + echo "GPIO out set" > /proc/gpio/GPIO73 + +} +stop() { + echo "Stopping robostix..." + + # Put the robostix into reset + echo "GPIO out clear" > /proc/gpio/GPIO73 +} +restart() { + stop + start +} + +case "$1" in + start) + start + ;; + stop) + stop + ;; + restart) + restart + ;; + *) + echo $"Usage: $0 {start|stop|restart}" + exit 1 +esac + +exit $? + diff --git a/packages/robostix-module/robostix-module.bb b/packages/robostix-module/robostix-module.bb new file mode 100644 index 0000000000..7f95adf341 --- /dev/null +++ b/packages/robostix-module/robostix-module.bb @@ -0,0 +1,36 @@ +DESCRIPTION = "Linux Driver for Gumstix robostix daughtercards" +SECTION = "base" +PRIORITY = "optional" +LICENSE = "GPL" +RDEPENDS = "kernel (${KERNEL_VERSION})" +DEPENDS = "virtual/kernel" + +PR = "r1" + +INITSCRIPT_NAME = "robostix" +INITSCRIPT_PARAMS = "defaults 10" + +SRC_URI = "\ + file://Makefile \ + file://robostix.h \ + file://robostix.c \ + file://robostix.init \ + " + +S = "${WORKDIR}" + +inherit module update-rc.d + +do_install() { + install -d ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + install -m 0644 ${WORKDIR}/robostix.ko ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + + install -d ${D}${sysconfdir}/init.d/ + install -m 0755 ${WORKDIR}/robostix.init ${D}${sysconfdir}/init.d/robostix +} + +PACKAGES = "${PN}" + +FILES_${PN} = "${base_libdir}/modules/" +FILES_${PN} += "${sysconfdir}/" + diff --git a/packages/robostix-utils/robostix-cmdline.bb b/packages/robostix-utils/robostix-cmdline.bb new file mode 100644 index 0000000000..0eecfc2e14 --- /dev/null +++ b/packages/robostix-utils/robostix-cmdline.bb @@ -0,0 +1,28 @@ +DESCRIPTION = "robostix programs" +SECTION = "base" +PRIORITY = "required" +PR = "r1" + +DEPENDS = robostix-module + +SRC_URI = " \ + file://robostix.h \ + file://robostix.c \ + " + +CMD_NAME=robostix + +S = "${WORKDIR}" + +do_compile () { + ${CC} -o ${CMD_NAME} *.c +} + +do_install () { + install -d ${D}${bindir}/ + install -m 0755 ${WORKDIR}/${CMD_NAME} ${D}${bindir}/ +} + +PACKAGES = "${PN}" +FILES_${PN} = "${bindir}/*" + diff --git a/packages/robostix-utils/robostix-cmdline/robostix.c b/packages/robostix-utils/robostix-cmdline/robostix.c new file mode 100644 index 0000000000..be47b5c5a9 --- /dev/null +++ b/packages/robostix-utils/robostix-cmdline/robostix.c @@ -0,0 +1,278 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* robostix.c +* +* PURPOSE: +* +* This implements the usermode program for talking to the robostix. +* +*****************************************************************************/ + +/* ---- Include Files ---------------------------------------------------- */ + +#include +#include +#include +#include + +#include "robostix.h" + +/* ---- Public Variables ------------------------------------------------- */ + +int gFd = -1; + +int gVal; + +/* ---- Private Constants and Types -------------------------------------- */ +/* ---- Private Variables ------------------------------------------------ */ + +typedef struct +{ + const char *cmdStr; + const char *argStr; + const char *helpStr; + int (*parseArgs)( int argc, char **argv ); + void (*execFunc)( int cmd ); + int cmd; + +} Cmd; + +int ParseNone( int argc, char **argv ); +int ParseOnOffArg( int argc, char **argv ); +int ParseOnOffPulseArg( int argc, char **argv ); +void Usage( void ); + +void Power( int cmd ); +void ReadIOctl( int cmd ); +void SimpleIOctl( int cmd ); + +Cmd gCmd[] = +{ + { "power", "on|off", "Controls the robostix voltage regulators", ParseOnOffArg, Power, -1 }, + { "reset", "on|off|pulse", "Resets the robostix", ParseOnOffPulseArg, SimpleIOctl, ROBOSTIX_IOCTL_RESET }, + { "245", "on|off", "Controls the 245 buffer chip", ParseOnOffArg, SimpleIOctl, ROBOSTIX_IOCTL_245_ENABLE }, + + { "sck", "on|off", "Sets/clears the SCK line", ParseOnOffArg, SimpleIOctl, ROBOSTIX_IOCTL_SET_SCK }, + { "ss", "on|off", "Sets/clears the SS line", ParseOnOffArg, SimpleIOctl, ROBOSTIX_IOCTL_SET_SS }, + { "txd", "on|off", "Sets/clears the IR-TXD line", ParseOnOffArg, SimpleIOctl, ROBOSTIX_IOCTL_SET_IR_TXD }, + { "mosi", "on|off", "Sets/clears the MOSI line", ParseOnOffArg, SimpleIOctl, ROBOSTIX_IOCTL_SET_MOSI }, + + { "rxd", "", "Reads the IR-RXD line", ParseNone, ReadIOctl, ROBOSTIX_IOCTL_GET_IR_RXD }, + { "irq", "", "Reads the TM-IRQ line", ParseNone, ReadIOctl, ROBOSTIX_IOCTL_GET_IRQ }, + { "miso", "", "Reads the MISO line", ParseNone, ReadIOctl, ROBOSTIX_IOCTL_GET_MISO }, + + { NULL } +}; + +/* ---- Private Function Prototypes -------------------------------------- */ +/* ---- Functions -------------------------------------------------------- */ + + +/**************************************************************************** +* +* main +* +***************************************************************************/ + +int main( int argc, char **argv ) +{ + char *cmdStr; + int argIdx; + Cmd *cmd; + + if ( argc == 1 ) + { + Usage( ); + exit( 0 ); + } + + if (( gFd = open( "/dev/robostix", O_RDWR )) < 0 ) + { + perror( "Unable to open /dev/robostix" ); + exit( 1 ); + } + + argIdx = 1; + cmdStr = argv[ argIdx++ ]; + + for ( cmd = gCmd; cmd->cmdStr != NULL; cmd++ ) + { + if ( strcasecmp( cmdStr, cmd->cmdStr ) == 0 ) + { + break; + } + } + if ( cmd->cmdStr == NULL ) + { + fprintf( stderr, "Unrecognized command: '%s'\n", cmdStr ); + exit( 1 ); + } + + if ( cmd->parseArgs( argc - argIdx, &argv[ argIdx ] )) + { + cmd->execFunc( cmd->cmd ); + } + + close( gFd ); + + exit( 0 ); + return 0; + +} // main + +/**************************************************************************** +* +* Checks to see if the argument is on/off (or equivalent) +* +***************************************************************************/ + +int IsOnOffArg( int argc, char **argv ) +{ + if (( strcasecmp( *argv, "on" ) == 0 ) + || ( strcasecmp( *argv, "t" ) == 0 ) + || ( strcasecmp( *argv, "1" ) == 0 )) + { + gVal = 1; + return 1; + } + + if (( strcasecmp( *argv, "off" ) == 0 ) + || ( strcasecmp( *argv, "f" ) == 0 ) + || ( strcasecmp( *argv, "0" ) == 0 )) + { + gVal = 0; + return 1; + } + + return 0; + +} // IsOnOffArg + +/**************************************************************************** +* +* Parses no arguments +* +***************************************************************************/ + +int ParseNone( int argc, char **argv ) +{ + return 1; + +} // ParseNone + +/**************************************************************************** +* +* Parses a command line argument for legel on/off values +* +***************************************************************************/ + +int ParseOnOffArg( int argc, char **argv ) +{ + if ( IsOnOffArg( argc, argv )) + { + return 1; + } + + fprintf( stderr, "Expecting on/off, found: '%s'\n", *argv ); + return 0; + +} // ParseOnOffArg + +/**************************************************************************** +* +* Parses a command line argument for legel on/off values +* +***************************************************************************/ + +int ParseOnOffPulseArg( int argc, char **argv ) +{ + if (( strcasecmp( *argv, "pulse" ) == 0 ) + || ( strcasecmp( *argv, "2" ) == 0 )) + { + gVal = 2; + return 1; + } + + if ( IsOnOffArg( argc, argv )) + { + return 1; + } + + fprintf( stderr, "Expecting on/off/pulse, found: '%s'\n", *argv ); + return 0; + +} // ParseOnoffPulseArg + +/**************************************************************************** +* +* Power +* +***************************************************************************/ + +void Power( int cmd ) +{ + SimpleIOctl( ROBOSTIX_IOCTL_POWER_VCC5 ); + +} // Power + +/**************************************************************************** +* +* SimpleIOctl +* +***************************************************************************/ + +void SimpleIOctl( int cmd ) +{ + if ( ioctl( gFd, cmd, gVal ) != 0 ) + { + fprintf( stderr, "ioctl call failed: %d\n", errno ); + } + +} // SimpleIOctl + +/**************************************************************************** +* +* SimpleIOctl +* +***************************************************************************/ + +void ReadIOctl( int cmd ) +{ + if ( ioctl( gFd, cmd, &gVal ) != 0 ) + { + fprintf( stderr, "ioctl call failed: %d\n", errno ); + } + +} // ReadIOctl + +/**************************************************************************** +* +* Usage +* +***************************************************************************/ + +void Usage( void ) +{ + Cmd *cmd; + + for ( cmd = gCmd; cmd->cmdStr != NULL; cmd++ ) + { + printf( "%-12s %-12s %s\n", cmd->cmdStr, cmd->argStr, cmd->helpStr ); + } + +} // Usage + diff --git a/packages/robostix-utils/robostix-cmdline/robostix.h b/packages/robostix-utils/robostix-cmdline/robostix.h new file mode 100644 index 0000000000..0d860bc7a4 --- /dev/null +++ b/packages/robostix-utils/robostix-cmdline/robostix.h @@ -0,0 +1,114 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* robostix_drv.h +* +* PURPOSE: +* +* This implements a driver for using the robostix from the gumstix +* +* Initially, this contains the required support to emulate enough of the +* parallel port interface to allow avrdude to program the ATMega128. +* +*****************************************************************************/ + +#if !defined( LINUX_ROBOSTIX_H ) +#define LINUX_ROBOSTIX_H ) + +/* ---- Include Files ----------------------------------------------------- */ + +#include + +/* ---- Constants and Types ----------------------------------------------- */ + +#define ROBOSTIX_MAJOR 240 + +#define ROBOSTIX_IOCTL_MAGIC 'R' + +/** + * Deefines for each of the commands. Note that since we want to reduce + * the possibility that a user mode program gets out of sync with a given + * driver, we explicitly assign a value to each enumeration. This makes + * it more difficult to stick new ioctl's in the middle of the list. + */ + +typedef enum +{ + ROBOSTIX_CMD_FIRST = 0x80, + + ROBOSTIX_CMD_POWER_VCC5 = 0x80, + ROBOSTIX_CMD_RESET = 0x81, + ROBOSTIX_CMD_245_ENABLE = 0x82, + ROBOSTIX_CMD_SET_SCK = 0x83, + ROBOSTIX_CMD_SET_SS = 0x84, + ROBOSTIX_CMD_SET_IR_TXD = 0x85, + ROBOSTIX_CMD_GET_IR_RXD = 0x86, + ROBOSTIX_CMD_SET_MOSI = 0x87, + ROBOSTIX_CMD_GET_MISO = 0x88, + ROBOSTIX_CMD_GET_IRQ = 0x89, + ROBOSTIX_CMD_DELAY_USEC = 0x8A, // value is hardocded in uisp DAPA.C + + /* Insert new ioctls here */ + + ROBOSTIX_CMD_LAST, + +} ROBOSTIX_CMD; + +/* + * The following are arguments to the various ioctl's + */ + +#define ROBOSTIX_PIN_OFF 0 +#define ROBOSTIX_PIN_ON 1 +#define ROBOSTIX_PIN_PULSE 2 // only used or Reset + +/* + * Definitions for the actual ioctl commands + */ + +#define ROBOSTIX_IOCTL_POWER_VCC5 _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_POWER_VCC5 ) // arg is int +#define ROBOSTIX_IOCTL_RESET _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_RESET ) // arg is int +#define ROBOSTIX_IOCTL_245_ENABLE _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_245_ENABLE ) // arg is int +#define ROBOSTIX_IOCTL_SET_SCK _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_SCK ) // arg is int +#define ROBOSTIX_IOCTL_SET_SS _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_SS ) // arg is int +#define ROBOSTIX_IOCTL_SET_IR_TXD _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_IR_TXD ) // arg is int +#define ROBOSTIX_IOCTL_GET_IR_RXD _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_IR_RXD, int ) // arg is int * +#define ROBOSTIX_IOCTL_SET_MOSI _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_SET_MOSI ) // arg is int +#define ROBOSTIX_IOCTL_GET_MISO _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_MISO, int ) // arg is int * +#define ROBOSTIX_IOCTL_GET_IRQ _IOR( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_GET_IRQ, int ) // arg is int * +#define ROBOSTIX_IOCTL_DELAY_USEC _IO( ROBOSTIX_IOCTL_MAGIC, ROBOSTIX_CMD_DELAY_USEC ) // arg is int + + +/* + * Definitions for sysctl. The top level define has to be unique system wide. + * The kernel defines values 1 thru about 10 (see include/linunx/sysctl.h) + */ + +#define CTL_ROBOSTIX 0x526F626F /* 'Robo' in hex form */ + +/* + * The following are for entries in /proc/sys/robostix + */ + +enum +{ + CTL_ROBOSTIX_DEBUG_TRACE = 101, + CTL_ROBOSTIX_DEBUG_IOCTL = 102, + CTL_ROBOSTIX_DEBUG_ERROR = 103 +}; + +#endif // LINUX_ROBOSTIX_H + diff --git a/packages/robostix-utils/robostix-sertest.bb b/packages/robostix-utils/robostix-sertest.bb new file mode 100644 index 0000000000..0196f6c8f3 --- /dev/null +++ b/packages/robostix-utils/robostix-sertest.bb @@ -0,0 +1,28 @@ +DESCRIPTION = "robostix programs" +SECTION = "base" +PRIORITY = "required" +PR = "r1" + +DEPENDS = robostix-module + +SRC_URI = " \ + file://sertest.c \ + " + +CMD_NAME=sertest +LDLIBS = -lpthread + +S = "${WORKDIR}" + +do_compile () { + ${CC} ${LDLIBS} -o ${CMD_NAME} *.c +} + +do_install () { + install -d ${D}${bindir}/ + install -m 0755 ${WORKDIR}/${CMD_NAME} ${D}${bindir}/ +} + +PACKAGES = "${PN}" +FILES_${PN} = "${bindir}/*" + diff --git a/packages/robostix-utils/robostix-sertest/sertest.c b/packages/robostix-utils/robostix-sertest/sertest.c new file mode 100644 index 0000000000..3f0cf7a6fc --- /dev/null +++ b/packages/robostix-utils/robostix-sertest/sertest.c @@ -0,0 +1,443 @@ +/**************************************************************************** +* +* Copyright (c) 2006 Dave Hylands +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* Alternatively, this software may be distributed under the terms of BSD +* license. +* +* See README and COPYING for more details. +* +****************************************************************************/ +/** +* +* sertest.c +* +* PURPOSE: +* +* This implements a sample program for accessing the serial port. +* +*****************************************************************************/ + +/* ---- Include Files ---------------------------------------------------- */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* ---- Public Variables ------------------------------------------------- */ + +int gFd = -1; + +int gVal; + +/* ---- Private Constants and Types -------------------------------------- */ +/* ---- Private Variables ------------------------------------------------ */ + +struct option gLongOption[] = +{ + // option A Flag V (has_arg, flag, val) + // ----------- - ---- --- + { "baud", 1, NULL, 'b' }, + { "debug", 0, NULL, 'd' }, + { "help", 0, NULL, 'h' }, + { "port", 1, NULL, 'p' }, + { "verbose", 0, NULL, 'v' }, + { 0 }, + +}; + +struct +{ + speed_t speed; + unsigned baudRate; +} gBaudTable[] = +{ + { B50, 50 }, + { B75, 75 }, + { B110, 110 }, + { B134, 134 }, + { B150, 150 }, + { B200, 200 }, + { B300, 300 }, + { B600, 600 }, + { B1200, 1200 }, + { B1800, 1800 }, + { B2400, 2400 }, + { B4800, 4800 }, + { B9600, 9600 }, + { B19200, 19200 }, + { B38400, 38400 }, + { B57600, 57600 }, + { B115200, 115200 }, + { B230400, 230400 } +}; + +#define ARRAY_LEN(x) ( sizeof( x ) / sizeof( x[ 0 ])) + +int gVerbose = 0; +int gDebug = 0; + +int gPortFd = -1; + +/* ---- Private Function Prototypes -------------------------------------- */ + +void *ReaderThread( void *param ); +char *StrMaxCpy( char *dst, const char *src, size_t maxLen ); +char *StrMaxCat( char *dst, const char *src, size_t maxLen ); +void Usage( void ); + +/* ---- Functions -------------------------------------------------------- */ + + +/*************************************************************************** +* +* main +* +****************************************************************************/ + +int main( int argc, char **argv ) +{ + int rc; + int opt; + char devName[ 40 ]; + const char *baudStr = NULL; + const char *portStr = "ttyS2"; + speed_t baudRate; + pthread_t readerThreadId; + + struct termios attr; + + // Parse the command line options + + while (( opt = getopt_long( argc, argv, "b:dhp:v", gLongOption, NULL )) > 0 ) + { + switch ( opt ) + { + case 'b': + { + baudStr = optarg; + break; + } + + case 'd': + { + gDebug = 1; + break; + } + + case 'p': + { + portStr = optarg; + break; + } + + case 'v': + { + gVerbose = 1; + break; + } + case '?': + case 'h': + { + Usage(); + return 1; + } + } + } + + devName[ 0 ] = '\0'; + if ( portStr[ 0 ] != '/' ) + { + StrMaxCpy( devName, "/dev/", sizeof( devName )); + } + StrMaxCat( devName, portStr, sizeof( devName )); + + + baudRate = B0; + if ( baudStr == NULL ) + { + baudRate = B9600; + } + else + { + int baudIdx; + int testBaud = atoi( baudStr ); + + for ( baudIdx = 0; baudIdx < ARRAY_LEN( gBaudTable ); baudIdx++ ) + { + if ( gBaudTable[ baudIdx ].baudRate == testBaud ) + { + baudRate = gBaudTable[ baudIdx ].speed; + break; + } + } + + if ( baudRate == B0 ) + { + fprintf( stderr, "Unrecognized baud rate: '%s'\n", baudStr ); + exit( 1 ); + } + } + + if (( gPortFd = open( devName, O_RDWR | O_EXCL )) < 0 ) + { + fprintf( stderr, "Unable to open serial port '%s': %s\n", devName, strerror( errno )); + exit( 2 ); + } + + if ( tcgetattr( gPortFd, &attr ) < 0 ) + { + fprintf( stderr, "Call to tcgetattr failed: %s\n", strerror( errno )); + exit( 3 ); + } + + attr.c_iflag = 0; + attr.c_oflag = 0; + attr.c_cflag = CLOCAL | CREAD | CS8; + attr.c_lflag = 0; + attr.c_cc[ VTIME ] = 0; // timeout in tenths of a second + attr.c_cc[ VMIN ] = 1; // Only wait for a single char + + cfsetispeed( &attr, baudRate ); + cfsetospeed( &attr, baudRate ); + + if ( tcsetattr( gPortFd, TCSAFLUSH, &attr ) < 0 ) + { + fprintf( stderr, "Call to tcsetattr failed: %s\n", strerror( errno )); + exit( 4 ); + } + + // Put stdin & stdout in unbuffered mode. + + setbuf( stdin, NULL ); + setbuf( stdout, NULL ); + + // Put stdin in raw mode (i.e. turn off canonical mode). Canonical mode + // causes the driver to wait for the RETURN character so that line editing + // can take place. We also want to turn off ECHO. + + { + struct termios tio; + + if ( tcgetattr( fileno( stdin ), &tio ) < 0 ) + { + fprintf( stderr, "Unable to retrieve terminal settings: %s\n", strerror( errno )); + exit( 5 ); + } + + tio.c_lflag &= ~( ICANON | ECHO ); + tio.c_cc[VTIME] = 0; + tio.c_cc[VMIN] = 1; + + if ( tcsetattr( fileno( stdin ), TCSANOW, &tio ) < 0 ) + { + fprintf( stderr, "Unable to update terminal settings: %s\n", strerror( errno )); + exit( 6 ); + } + } + + // Kick off the serial port reader thread. + + rc = pthread_create( &readerThreadId, NULL, ReaderThread, NULL ); + if ( rc != 0 ) + { + fprintf( stderr, "Error creating ReaderThread: %s\n", strerror( rc )); + exit( 7 ); + } + + // Read stdin and send rcvd chars to the serial port + + while ( 1 ) + { + char ch; + int chInt = fgetc( stdin ); + if ( chInt < 0 ) + { + fprintf( stderr, "Exiting...\n" ); + break; + } + ch = (char)chInt; + + if ( gDebug ) + { + if (( ch < ' ' ) || ( ch > '~' )) + { + fprintf( stderr, "stdin Read: 0x%02x '.'\n", ch ); + } + else + { + fprintf( stderr, "stdin Read: 0x%02x '%c'\n", ch, ch ); + } + + } + + if ( write( gPortFd, &ch, 1 ) != 1 ) + { + fprintf( stderr, "write to serial port failed: %s\n", strerror( errno )); + break; + } + } + + + close( gPortFd ); + + exit( 0 ); + return 0; // Get rid of warning about not returning anything +} + +/***************************************************************************/ +/** +* Thread which processes the incoming serial data. +*/ + +void *ReaderThread( void *param ) +{ + while ( 1 ) + { + char ch; + int bytesRead; + + if (( bytesRead = read( gPortFd, &ch, 1 )) < 0 ) + { + fprintf( stderr, "Serial port read failed: %s\n", strerror( errno )); + exit( 1 ); + } + + if ( gDebug ) + { + if (( ch < ' ' ) || ( ch > '~' )) + { + fprintf( stderr, "Serial Read: 0x%02x '.'\n", ch ); + } + else + { + fprintf( stderr, "Serial Read: 0x%02x '%c'\n", ch, ch ); + } + + } + + putc( ch, stdout ); + } + + return 0; + +} // ReaderThread + +/***************************************************************************/ +/** +* Concatenates source to the destination, but makes sure that the +* destination string (including terminating null), doesn't exceed maxLen. +* +* @param dst (mod) String to concatnate onto. +* @param src (in) String to being added to the end of @a dst. +* @param maxLen (in) Maximum length that @a dst is allowed to be. +* +* @return A pointer to the destination string. +*/ + +char *StrMaxCat( char *dst, const char *src, size_t maxLen ) +{ + size_t dstLen = strlen( dst ); + + if ( dstLen < maxLen ) + { + StrMaxCpy( &dst[ dstLen ], src, maxLen - dstLen ); + } + + return dst; + +} /* StrMaxCat */ + +/***************************************************************************/ +/** +* Copies the source to the destination, but makes sure that the +* destination string (including terminating null), doesn't exceed +* maxLen. +* +* @param dst (out) Place to store the string copy. +* @param src (in) String to copy. +* @param maxLen (in) Maximum number of characters to copy into @a dst. +* +* @return A pointer to the destination string. +*/ + +char *StrMaxCpy( char *dst, const char *src, size_t maxLen ) +{ + if ( maxLen < 1 ) + { + /* + * There's no room in the buffer? + */ + + return ""; + } + + if ( maxLen == 1 ) + { + /* + * There's only room for the terminating null character + */ + + dst[ 0 ] = '\0'; + return dst; + } + + /* + * The Visual C++ version of strncpy writes to every single character + * of the destination buffer, so we use a length one character smaller + * and write in our own null (if required). + * + * This allows the caller to store a sentinel in the last byte of the + * buffer to detect overflows (if desired). + */ + + strncpy( dst, src, maxLen - 1 ); + if (( strlen( src ) + 1 ) >= maxLen ) + { + /* + * The string exactly fits, or probably overflows the buffer. + * Write in the terminating null character since strncpy doesn't in + * this particular case. + * + * We don't do this arbitrarily so that the caller can use a sentinel + * in the very end of the buffer to detect buffer overflows. + */ + + dst[ maxLen - 1 ] = '\0'; + } + + return dst; + +} /* StrMaxCpy */ + +/*************************************************************************** +* +* Usage +* +****************************************************************************/ + +void Usage() +{ + fprintf( stderr, "Usage: sertest [option(s)]\n" ); + fprintf( stderr, " Download a program via serial/i2c\n" ); + fprintf( stderr, "\n" ); + fprintf( stderr, " -b, --baud=baud Set the baudrate used\n" ); + fprintf( stderr, " -d, --debug Turn on debug output\n" ); + fprintf( stderr, " -h, --help Display this message\n" ); + fprintf( stderr, " -p, --port=port Set the I/O port\n" ); + fprintf( stderr, " -v, --verbose Turn on verbose messages\n" ); + +} // Usage + + diff --git a/packages/robostix/robostix.bb b/packages/robostix/robostix.bb new file mode 100644 index 0000000000..5e1f8c8b69 --- /dev/null +++ b/packages/robostix/robostix.bb @@ -0,0 +1,135 @@ +DESCRIPTION = "Robostix programs" +PRIORITY = "optional" +SECTION = "base" +LICENSE = "GPL" +RDEPENDS = "kernel (${KERNEL_VERSION})" +DEPENDS = "virtual/kernel" + +PR = "r0" + +SRC_URI = "svn://svn.gumstix.com/gumstix-buildroot/branches/projects;module=robostix;rev=1588;proto=http \ + file://makefile-rules.patch;patch=1 \ + file://gummake.patch;patch=1 \ + " + +S = "${WORKDIR}/robostix" + +inherit module-base + +EXTRA_OEMAKE = 'CROSS_COMPILE="${CROSS_COMPILE}" \ + KERNELDIR="${KERNEL_SOURCE}" \ + CC="${CC}" \ + ' + +PARALLEL_MAKE = "" + +do_configure () { + echo "Nothing to configure for robostix" +} + +do_compile () { + unset CFLAGS CPPFLAGS CXXFLAGS LDFLAGS + cd ${S} + make + cd ${S}/gumstix + oe_runmake + cd ${S}/gumstix/i2c-io + oe_runmake + cd ${S}/gumstix/i2c-load + oe_runmake + cd ${S}/gumstix/i2c + oe_runmake +} + +do_install () { + # install programs to bindir + install -m 0755 -d ${D}${bindir} + install -m 0755 ${S}/gumstix/i2c-io/i2c-io ${D}${bindir} + install -m 0755 ${S}/gumstix/i2c-load/i2c-load ${D}${bindir} + install -m 0755 ${S}/gumstix/i2c/i2c ${D}${bindir} + install -m 0755 ${S}/gumstix/robostix ${D}${bindir} + install -m 0755 ${S}/gumstix/sertest ${D}${bindir} + + # kernel module installs with other modules, but use + # cp instead of install so its not stripped + install -m 0755 -d ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + cp ${S}/gumstix/robostix_drv.ko ${D}${base_libdir}/modules/${KERNEL_VERSION}/extra/ + + # avr hex programs install to /root + install -m 0755 -d ${D}/root + install -m 0755 ${S}/ArgTest/ArgTest.hex ${D}/root + install -m 0755 ${S}/Flash-LED/Flash-LED.hex ${D}/root + install -m 0755 ${S}/i2c-BootLoader/i2c-Boot-m128-16MHz.hex ${D}/root + install -m 0755 ${S}/i2c-BootLoader/i2c-Boot-m128-16MHz-eep.hex ${D}/root + install -m 0755 ${S}/i2c-io/i2c-io.hex ${D}/root + install -m 0755 ${S}/i2c-test/i2c-test.hex ${D}/root + install -m 0755 ${S}/int6/int6.hex ${D}/root + install -m 0755 ${S}/LCD-Test/LCD-Test.hex ${D}/root + install -m 0755 ${S}/QD-Test/QD-Test.hex ${D}/root + install -m 0755 ${S}/RCInput/RC-Test.hex ${D}/root + install -m 0755 ${S}/Simple-Flasher/Simple-Flasher.hex ${D}/root + install -m 0755 ${S}/Simple-Servo/Simple-Servo.hex ${D}/root + install -m 0755 ${S}/Simple-Servo-2/Simple-Servo-2.hex ${D}/root + install -m 0755 ${S}/Tachometer/Tachometer.hex ${D}/root +} + +PACKAGES = "${PN}-i2c-io" +FILES_${PN}-i2c-io = "${bindir}/i2c-io" + +PACKAGES += "${PN}-i2c-load" +FILES_${PN}-i2c-load = "${bindir}/i2c-load" + +PACKAGES += "${PN}-i2c" +FILES_${PN}-i2c = "${bindir}/i2c" + +PACKAGES += "${PN}-sertest" +FILES_${PN}-sertest = "${bindir}/sertest" + +PACKAGES += "${PN}-usermode" +FILES_${PN}-usermode = "${bindir}/robostix" + +PACKAGES += "${PN}-kernel-module" +FILES_${PN}-kernel-module = "${base_libdir}/modules/${KERNEL_VERSION}/extra/robostix_drv.ko" + +PACKAGES += "${PN}-avr-ArgTest" +FILES_${PN}-avr-ArgTest = "/root/ArgTest.hex" + +PACKAGES += "${PN}-avr-Flash-LED" +FILES_${PN}-avr-Flash-LED = "/root/Flash-LED.hex" + +PACKAGES += "${PN}-avr-i2c-BootLoader" +FILES_${PN}-avr-i2c-BootLoader = "/root/i2c-Boot-m128-16MHz.hex" + +PACKAGES += "${PN}-avr-i2c-BootLoader-eep" +FILES_${PN}-avr-i2c-BootLoader-eep = "/root/i2c-Boot-m128-16MHz-eep.hex" + +PACKAGES += "${PN}-avr-i2c-io" +FILES_${PN}-avr-i2c-io = "/root/i2c-io.hex" + +PACKAGES += "${PN}-avr-i2c-test" +FILES_${PN}-avr-i2c-test = "/root/i2c-test.hex" + +PACKAGES += "${PN}-avr-int6" +FILES_${PN}-avr-int6 = "/root/int6.hex" + +PACKAGES += "${PN}-avr-LCD-Test" +FILES_${PN}-avr-LCD-Test = "/root/LCD-Test.hex" + +PACKAGES += "${PN}-avr-QD-Test" +FILES_${PN}-avr-QD-Test = "/root/QD-Test.hex" + +PACKAGES += "${PN}-avr-RC-Test" +FILES_${PN}-avr-RC-Test = "/root/RC-Test.hex" + +PACKAGES += "${PN}-avr-Simple-Flasher" +FILES_${PN}-avr-Simple-Flasher = "/root/Simple-Flasher.hex" + +PACKAGES += "${PN}-avr-Simple-Servo" +FILES_${PN}-avr-Simple-Servo = "/root/Simple-Servo.hex" + +PACKAGES += "${PN}-avr-Simple-Servo-2" +FILES_${PN}-avr-Simple-Servo-2 = "/root/Simple-Servo-2.hex" + +PACKAGES += "${PN}-avr-Tachometer" +FILES_${PN}-avr-Tachometer = "/root/Tachometer.hex" + diff --git a/packages/robostix/robostix/gummake.patch b/packages/robostix/robostix/gummake.patch new file mode 100644 index 0000000000..0b968592b5 --- /dev/null +++ b/packages/robostix/robostix/gummake.patch @@ -0,0 +1,26 @@ +--- robostix/gumstix/Makefile.orig 2008-03-08 11:37:50.000000000 -0700 ++++ robostix/gumstix/Makefile 2008-03-08 11:36:55.000000000 -0700 +@@ -32,10 +32,10 @@ + + PWD := $(shell pwd) + +-GUMSTIX_BUILDROOT = $(PWD)/../../gumstix-buildroot +-BUILD_ARM = $(GUMSTIX_BUILDROOT)/build_arm_nofpu +-KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) +-CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- ++#GUMSTIX_BUILDROOT = $(PWD)/../../gumstix-buildroot ++#BUILD_ARM = $(GUMSTIX_BUILDROOT)/build_arm_nofpu ++#KERNELDIR ?= $(wildcard $(BUILD_ARM)/linux-*) ++#CROSS_COMPILE = $(BUILD_ARM)/staging_dir/bin/arm-linux- + + default: svn-version.h user-app kernel-module + +@@ -47,7 +47,7 @@ + user-app: robostix sertest + + TARGET_ARCH=-Os -march=armv5te -mtune=xscale -Wa,-mcpu=xscale +-CC = $(CROSS_COMPILE)gcc ++#CC = $(CROSS_COMPILE)gcc + + robostix: robostix.c + diff --git a/packages/robostix/robostix/makefile-rules.patch b/packages/robostix/robostix/makefile-rules.patch new file mode 100644 index 0000000000..f00d2884e8 --- /dev/null +++ b/packages/robostix/robostix/makefile-rules.patch @@ -0,0 +1,25 @@ +--- robostix/Rules.mk.orig 2008-03-08 10:36:37.000000000 -0700 ++++ robostix/Rules.mk 2008-03-08 10:37:14.000000000 -0700 +@@ -24,21 +24,7 @@ + vpath %.c ../Common ../Shared + vpath %.S ../Common ../Shared + +-CFLAGS += -Os \ +- -Wall \ +- -Werror \ +- -Wimplicit \ +- -Wpointer-arith \ +- -Wswitch \ +- -Wredundant-decls \ +- -Wreturn-type \ +- -Wshadow \ +- -Wunused \ +- -Wcast-qual \ +- -Wnested-externs \ +- -Wmissing-prototypes \ +- -Wstrict-prototypes \ +- -Wmissing-declarations ++CFLAGS += -Os + + CPPFLAGS += $(AVR_MCU_FLAGS) -I . -I ../Common -I ../Shared + LDFLAGS += $(AVR_MCU_FLAGS) -Wl,-Map,$(basename $@).map -- cgit v1.2.3