added picctl code
authorroot@rika
Wed, 06 Feb 2008 17:37:50 +0000
changeset 537602e25a04a
parent 4 df6a40031aa5
child 6 611d053f0972
added picctl code
graphlcd-base/glcddrivers/Makefile
graphlcd-base/glcddrivers/drivers.c
graphlcd-base/glcddrivers/picctl.c
graphlcd-base/glcddrivers/picctl.h
graphlcd-base/glcddrivers/port.c
graphlcd-base/glcddrivers/port.h
     1.1 --- a/graphlcd-base/glcddrivers/Makefile	Wed Feb 06 17:32:55 2008 +0000
     1.2 +++ b/graphlcd-base/glcddrivers/Makefile	Wed Feb 06 17:37:50 2008 +0000
     1.3 @@ -14,7 +14,7 @@
     1.4  
     1.5  LIBNAME = $(BASENAME).$(VERMAJOR).$(VERMINOR).$(VERMICRO)
     1.6  
     1.7 -OBJS = common.o config.o driver.o drivers.o port.o simlcd.o framebuffer.o gu140x32f.o gu256x64-372.o gu256x64-3900.o hd61830.o ks0108.o image.o sed1330.o sed1520.o t6963c.o noritake800.o serdisp.o avrctl.o g15daemon.o network.o gu126x64D-K610A4.o
     1.8 +OBJS = common.o config.o driver.o drivers.o port.o simlcd.o framebuffer.o gu140x32f.o gu256x64-372.o gu256x64-3900.o hd61830.o ks0108.o image.o sed1330.o sed1520.o t6963c.o noritake800.o serdisp.o avrctl.o g15daemon.o network.o gu126x64D-K610A4.o picctl.o
     1.9  
    1.10  HEADERS = config.h driver.h drivers.h
    1.11  
     2.1 --- a/graphlcd-base/glcddrivers/drivers.c	Wed Feb 06 17:32:55 2008 +0000
     2.2 +++ b/graphlcd-base/glcddrivers/drivers.c	Wed Feb 06 17:37:50 2008 +0000
     2.3 @@ -12,6 +12,7 @@
     2.4  #include <string.h>
     2.5  
     2.6  #include "drivers.h"
     2.7 +#include "picctl.h"
     2.8  #include "simlcd.h"
     2.9  #include "gu140x32f.h"
    2.10  #include "gu256x64-372.h"
    2.11 @@ -48,6 +49,7 @@
    2.12      {"image",         kDriverImage},
    2.13      {"noritake800",   kDriverNoritake800},
    2.14      {"avrctl",        kDriverAvrCtl},
    2.15 +    {"picctl",        kDriverPICCtl},
    2.16      {"network",       kDriverNetwork},
    2.17      {"gu126x64D-K610A4", kDriverGU126X64D_K610A4},
    2.18      {"serdisp",       kDriverSerDisp},
    2.19 @@ -100,6 +102,8 @@
    2.20              return new cDriverNoritake800(config);
    2.21          case kDriverAvrCtl:
    2.22              return new cDriverAvrCtl(config);
    2.23 +        case kDriverPICCtl:
    2.24 +            return cDriverPICCtl::getInstance(config);
    2.25          case kDriverNetwork:
    2.26              return new cDriverNetwork(config);
    2.27          case kDriverGU126X64D_K610A4:
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/graphlcd-base/glcddrivers/picctl.c	Wed Feb 06 17:37:50 2008 +0000
     3.3 @@ -0,0 +1,398 @@
     3.4 +/*
     3.5 + * GraphLCD driver library
     3.6 + *
     3.7 + * picctl.c  -  PIC controlled LCD driver class
     3.8 + *
     3.9 + * This file is released under the GNU General Public License. Refer
    3.10 + * to the COPYING file distributed with this package.
    3.11 + *
    3.12 + * Codebase by Andreas Regel <andreas.regel AT powarman.de>
    3.13 + * (c) 2007 Carsten Presser
    3.14 + */
    3.15 +
    3.16 +#include <stdint.h>
    3.17 +#include <syslog.h>
    3.18 +#include <math.h>
    3.19 +
    3.20 +#include "common.h"
    3.21 +#include "config.h"
    3.22 +#include "port.h"
    3.23 +#include "picctl.h"
    3.24 +
    3.25 +
    3.26 +
    3.27 +namespace GLCD
    3.28 +{
    3.29 +
    3.30 +/* command header:
    3.31 +**  8 bits  sync byte (0xAA for sent commands, 0x55 for received commands)
    3.32 +**  8 bits  command id
    3.33 +** 16 bits  command length (excluding header)
    3.34 +*/
    3.35 +const unsigned char CMD_HDR_SYNC    = 0;
    3.36 +const unsigned char CMD_HDR_COMMAND = 1;
    3.37 +const unsigned char CMD_HDR_LENGTH  = 2;
    3.38 +const unsigned char CMD_DATA_START  = 4;
    3.39 +
    3.40 +const unsigned char CMD_SYNC_SEND = 0xAA;
    3.41 +const unsigned char CMD_SYNC_RECV = 0x55;
    3.42 +
    3.43 +
    3.44 +const unsigned char CMD_SYS_SYNC =		0x00;
    3.45 +const unsigned char CMD_SYS_ACK	=		0x01;
    3.46 +const unsigned char CMD_SYS_NACK =		0x02;
    3.47 +const unsigned char CMD_SYS_NIMP =		0xFF;
    3.48 +const unsigned char CMD_SYS_IR =		0x10;
    3.49 +
    3.50 +const unsigned char CMD_DISP_CLEAR_SCREEN =	0x10;
    3.51 +const unsigned char CMD_DISP_SET_ROW_DATA =  	0x14;
    3.52 +const unsigned char CMD_DISP_SET_ADDRESS =	0x16;
    3.53 +
    3.54 +const unsigned char CMD_READ_CLOCK =		0x40;
    3.55 +const unsigned char CMD_WRITE_CLOCK =		0x41;
    3.56 +const unsigned char CMD_SET_PWM1 =		0x45;
    3.57 +const unsigned char CMD_SET_PWM2 =		0x46;
    3.58 +
    3.59 +const unsigned char CMD_SET_MODE_MANAGED =	0x70;
    3.60 +const unsigned char CMD_SET_MODE_UNMANAGED =	0x71;
    3.61 +
    3.62 +const unsigned char CMD_BOOT =			0x80;
    3.63 +// singleton
    3.64 +cDriverPICCtl* cDriverPICCtl::instance = 0;
    3.65 +
    3.66 +cDriverPICCtl* cDriverPICCtl::getInstance(cDriverConfig * config)
    3.67 +{
    3.68 +    if (!instance)
    3.69 +        instance = new cDriverPICCtl(config);
    3.70 +    return instance;
    3.71 +}
    3.72 +// end singleton-pattern
    3.73 +
    3.74 +
    3.75 +
    3.76 +cDriverPICCtl::cDriverPICCtl(cDriverConfig * config)
    3.77 +:   config(config)
    3.78 +{
    3.79 +    oldConfig = new cDriverConfig(*config);
    3.80 +
    3.81 +    port = new cSerialPort();
    3.82 +
    3.83 +    //width = config->width;
    3.84 +    //height = config->height;
    3.85 +    refreshCounter = 0;
    3.86 +    ack_flag = false;
    3.87 +}
    3.88 +
    3.89 +cDriverPICCtl::~cDriverPICCtl()
    3.90 +{
    3.91 +    delete port;
    3.92 +    delete oldConfig;
    3.93 +}
    3.94 +
    3.95 +void cDriverPICCtl::SignalHandler(int signal)
    3.96 +{
    3.97 +    unsigned char buf[255];
    3.98 +    int numbytes,i;
    3.99 +
   3.100 +    numbytes = instance->port->ReadData(buf,255);
   3.101 +
   3.102 +
   3.103 +    if ((buf[CMD_HDR_SYNC] == CMD_SYNC_RECV) && (buf[CMD_HDR_LENGTH+1] == (numbytes - CMD_DATA_START)))
   3.104 +    {
   3.105 +    	switch (buf[CMD_HDR_COMMAND])
   3.106 +	{
   3.107 +	  case CMD_SYS_ACK:	instance->ack_flag = true;
   3.108 +	  			break;
   3.109 +
   3.110 +	  case CMD_SYS_IR:	printf(" Incoming Key-Event 0x%02x (Source 0x%02x)\n",buf[CMD_DATA_START+1],buf[CMD_DATA_START]);
   3.111 +	  			break;
   3.112 +
   3.113 +	  default:		printf(" recieved Message 0x%x \n",buf[CMD_HDR_COMMAND]);
   3.114 +	}
   3.115 +    }
   3.116 +    else
   3.117 +    {
   3.118 +        syslog(LOG_INFO, "PICCtl received a malformed packet.\n");
   3.119 +        for (i=0; i<numbytes; i++)
   3.120 +        {
   3.121 +            printf(" 0x%x",buf[i]);
   3.122 +        }
   3.123 +        printf("; recieved %d bytes2\n",numbytes);
   3.124 +    }
   3.125 +
   3.126 +}
   3.127 +
   3.128 +int cDriverPICCtl::Init()
   3.129 +{
   3.130 +    int y;
   3.131 +
   3.132 +    // fixed values so far...
   3.133 +    width = 240;
   3.134 +    height = 64;
   3.135 +
   3.136 +    for (unsigned int i = 0; i < config->options.size(); i++)
   3.137 +    {
   3.138 +        if (config->options[i].name == "")
   3.139 +        {
   3.140 +        }
   3.141 +    }
   3.142 +
   3.143 +    // setup lcd array (wanted state)
   3.144 +    newLCD = new unsigned char*[height];
   3.145 +    if (newLCD)
   3.146 +    {
   3.147 +        for (y = 0; y < height; y++)
   3.148 +        {
   3.149 +            newLCD[y] = new unsigned char[width/8];
   3.150 +            memset(newLCD[y], 0, (width/8));
   3.151 +        }
   3.152 +    }
   3.153 +    // setup lcd array (current state)
   3.154 +    oldLCD = new unsigned char*[height];
   3.155 +    if (oldLCD)
   3.156 +    {
   3.157 +        for (y = 0; y < height; y++)
   3.158 +        {
   3.159 +            oldLCD[y] = new unsigned char[width/8];
   3.160 +            memset(oldLCD[y], 0, (width/8));
   3.161 +        }
   3.162 +    }
   3.163 +
   3.164 +    if (config->device == "")
   3.165 +    {
   3.166 +        return -1;
   3.167 +    }
   3.168 +    if (port->Open(config->device.c_str(), SignalHandler) != 0)
   3.169 +        return -1;
   3.170 +
   3.171 +    *oldConfig = *config;
   3.172 +
   3.173 +    // clear display
   3.174 +    Clear();
   3.175 +    CmdDispClearScreen();
   3.176 +    CmdDispSetManaged();
   3.177 +    CmdDispSetBrightness(100);
   3.178 +
   3.179 +    syslog(LOG_INFO, "%s: PICCtl initialized.\n", config->name.c_str());
   3.180 +    return 0;
   3.181 +}
   3.182 +
   3.183 +int cDriverPICCtl::DeInit()
   3.184 +{
   3.185 +    int y;
   3.186 +    // free lcd array (wanted state)
   3.187 +    if (newLCD)
   3.188 +    {
   3.189 +        for (y = 0; y < height; y++)
   3.190 +        {
   3.191 +            delete[] newLCD[y];
   3.192 +        }
   3.193 +        delete[] newLCD;
   3.194 +    }
   3.195 +    // free lcd array (current state)
   3.196 +    if (oldLCD)
   3.197 +    {
   3.198 +        for (y = 0; y < height; y++)
   3.199 +        {
   3.200 +            delete[] oldLCD[y];
   3.201 +        }
   3.202 +        delete[] oldLCD;
   3.203 +    }
   3.204 +
   3.205 +    CmdDispSetUnManaged();
   3.206 +    
   3.207 +    delete instance;
   3.208 +    instance = 0;
   3.209 +
   3.210 +    if (port->Close() != 0)
   3.211 +        return -1;
   3.212 +    return 0;
   3.213 +}
   3.214 +
   3.215 +int cDriverPICCtl::CheckSetup()
   3.216 +{
   3.217 +    if (config->device != oldConfig->device ||
   3.218 +        config->width != oldConfig->width ||
   3.219 +        config->height != oldConfig->height)
   3.220 +    {
   3.221 +        DeInit();
   3.222 +        Init();
   3.223 +        return 0;
   3.224 +    }
   3.225 +
   3.226 +    if (config->upsideDown != oldConfig->upsideDown ||
   3.227 +        config->invert != oldConfig->invert)
   3.228 +    {
   3.229 +        oldConfig->upsideDown = config->upsideDown;
   3.230 +        oldConfig->invert = config->invert;
   3.231 +        return 1;
   3.232 +    }
   3.233 +    return 0;
   3.234 +}
   3.235 +
   3.236 +void cDriverPICCtl::Clear()
   3.237 +{
   3.238 +    for (int y = 0; y < height; y++)
   3.239 +        memset(newLCD[y], 0, (width/8));
   3.240 +}
   3.241 +
   3.242 +void cDriverPICCtl::Set8Pixels(int x, int y, unsigned char data)
   3.243 +{
   3.244 +    if (x >= width || y >= height)
   3.245 +        return;
   3.246 +
   3.247 +    if (!config->upsideDown)
   3.248 +    {
   3.249 +        newLCD[y][x/8] = data;
   3.250 +    }
   3.251 +    else
   3.252 +    {
   3.253 +        x = width - 1 - x;
   3.254 +        y = height - 1 - y;
   3.255 +        newLCD[y][x / 8] |= ReverseBits(data);
   3.256 +    }
   3.257 +}
   3.258 +
   3.259 +void cDriverPICCtl::Refresh(bool refreshAll)
   3.260 +{
   3.261 +    int y;
   3.262 +
   3.263 +    if (CheckSetup() == 1)
   3.264 +        refreshAll = true;
   3.265 +
   3.266 +    if (config->refreshDisplay > 0)
   3.267 +    {
   3.268 +        refreshCounter = (refreshCounter + 1) % config->refreshDisplay;
   3.269 +        if (!refreshAll && !refreshCounter)
   3.270 +            refreshAll = true;
   3.271 +    }
   3.272 +
   3.273 +
   3.274 +    if (refreshAll)
   3.275 +    {
   3.276 +        // draw all
   3.277 +        // always draw a complete row! (30 bytes!)
   3.278 +        for (y = 0; y < height; y++)
   3.279 +        {
   3.280 +            CmdDispSetColData(y, 0, (width/8), newLCD[y]);
   3.281 +            memcpy(oldLCD[y], newLCD[y], (width/8));
   3.282 +        }
   3.283 +        // and reset RefreshCounter
   3.284 +        refreshCounter = 0;
   3.285 +    }
   3.286 +    else
   3.287 +    {
   3.288 +	// for every line
   3.289 +	for (y = 0; y< height; y++)
   3.290 +        {
   3.291 +            // did anysthing change? -> draw new line
   3.292 +	    if (memcmp(newLCD[y],oldLCD[y],(width/8)) != 0)
   3.293 +            {
   3.294 +                 CmdDispSetColData(y, 0, (width/8), newLCD[y]);
   3.295 +                 memcpy(oldLCD[y], newLCD[y], (width/8));
   3.296 +            }
   3.297 +        }
   3.298 +    }
   3.299 +}
   3.300 +
   3.301 +void cDriverPICCtl::SetBrightness(unsigned int percent)
   3.302 +{
   3.303 +    CmdDispSetBrightness(percent);
   3.304 +}
   3.305 +
   3.306 +void cDriverPICCtl::SetClock(unsigned int percent)
   3.307 +{
   3.308 +    CmdDispSetBrightness(percent);
   3.309 +}
   3.310 +
   3.311 +int cDriverPICCtl::WaitForAck(void)
   3.312 +{
   3.313 +    int timeout;
   3.314 +
   3.315 +    for (timeout=0; timeout<10000; timeout++)
   3.316 +    {
   3.317 +    	usleep(10);
   3.318 +	if (ack_flag) return 1;
   3.319 +    }
   3.320 +    syslog(LOG_INFO, "PICCtl: missed a ACK packet!.\n");
   3.321 +    return 0;
   3.322 +}
   3.323 +
   3.324 +void cDriverPICCtl::CmdDispClearScreen(void)
   3.325 +{
   3.326 +    uint8_t cmd[4];
   3.327 +
   3.328 +    cmd[CMD_HDR_SYNC] = CMD_SYNC_SEND;
   3.329 +    cmd[CMD_HDR_COMMAND] = CMD_DISP_CLEAR_SCREEN;
   3.330 +    cmd[CMD_HDR_LENGTH] = 0;
   3.331 +    cmd[CMD_HDR_LENGTH+1] = 0;
   3.332 +
   3.333 +    port->WriteData(cmd, 4);
   3.334 +    WaitForAck();
   3.335 +}
   3.336 +
   3.337 +void cDriverPICCtl::CmdDispSetBrightness(uint8_t percent)
   3.338 +{
   3.339 +    uint8_t cmd[5];
   3.340 +
   3.341 +    cmd[CMD_HDR_SYNC] = CMD_SYNC_SEND;
   3.342 +    cmd[CMD_HDR_COMMAND] = CMD_SET_PWM1;
   3.343 +    cmd[CMD_HDR_LENGTH] = 0;
   3.344 +    cmd[CMD_HDR_LENGTH+1] = 1;
   3.345 +    cmd[CMD_DATA_START] = (uint8_t) round(percent * 2.55);
   3.346 +
   3.347 +    port->WriteData(cmd, 5);
   3.348 +    WaitForAck();
   3.349 +}
   3.350 +
   3.351 +void cDriverPICCtl::CmdDispSetColData(uint8_t yoffset, uint8_t xoffset, uint8_t length, uint8_t * data)
   3.352 +{
   3.353 +    uint8_t cmd[64];
   3.354 +    uint16_t address;
   3.355 +
   3.356 +    address = 0x1E * yoffset + xoffset;
   3.357 +
   3.358 +    cmd[CMD_HDR_SYNC] = CMD_SYNC_SEND;
   3.359 +    cmd[CMD_HDR_COMMAND] = CMD_DISP_SET_ROW_DATA;
   3.360 +    cmd[CMD_HDR_LENGTH] = 0;
   3.361 +    cmd[CMD_HDR_LENGTH+1] = (length + 2);
   3.362 +    cmd[CMD_DATA_START] = (uint8_t)(address % 256);	// lower address
   3.363 +    cmd[CMD_DATA_START+1] = (uint8_t)(address / 256);	// upper address
   3.364 +    memcpy(&cmd[CMD_DATA_START+2], data, length);
   3.365 +
   3.366 +    port->WriteData(cmd, length + 6);
   3.367 +    WaitForAck();
   3.368 +
   3.369 +//    for (address = 0; address < length+6; address ++) printf("0x%02x ",cmd[address]);
   3.370 +//  printf("address=0x%x upper=0x%x lower=0x%x \n", address, (uint8_t)(address / 256), (uint8_t)(address % 256));
   3.371 +//    printf("\n");
   3.372 +}
   3.373 +
   3.374 +void cDriverPICCtl::CmdDispSetManaged(void)
   3.375 +{
   3.376 +    uint8_t cmd[4];
   3.377 +
   3.378 +    cmd[CMD_HDR_SYNC] = CMD_SYNC_SEND;
   3.379 +    cmd[CMD_HDR_COMMAND] = CMD_SET_MODE_MANAGED;
   3.380 +    cmd[CMD_HDR_LENGTH] = 0;
   3.381 +    cmd[CMD_HDR_LENGTH+1] = 0;
   3.382 +
   3.383 +    port->WriteData(cmd,4);
   3.384 +    WaitForAck();
   3.385 +}
   3.386 +
   3.387 +void cDriverPICCtl::CmdDispSetUnManaged(void)
   3.388 +{
   3.389 +    uint8_t cmd[4];
   3.390 +
   3.391 +    cmd[CMD_HDR_SYNC] = CMD_SYNC_SEND;
   3.392 +    cmd[CMD_HDR_COMMAND] = CMD_SET_MODE_UNMANAGED;
   3.393 +    cmd[CMD_HDR_LENGTH] = 0;
   3.394 +    cmd[CMD_HDR_LENGTH+1] = 0;
   3.395 +
   3.396 +    port->WriteData(cmd,4);
   3.397 +    WaitForAck();
   3.398 +}
   3.399 +
   3.400 +
   3.401 +} // end NameSpace
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/graphlcd-base/glcddrivers/picctl.h	Wed Feb 06 17:37:50 2008 +0000
     4.3 @@ -0,0 +1,68 @@
     4.4 +/*
     4.5 + * GraphLCD driver library
     4.6 + *
     4.7 + * picctl.c  -  PIC controlled LCD driver class
     4.8 + *
     4.9 + * This file is released under the GNU General Public License. Refer
    4.10 + * to the COPYING file distributed with this package.
    4.11 + *
    4.12 + * Codebase by Andreas Regel <andreas.regel AT powarman.de>
    4.13 + * (c) 2007 Carsten Presser
    4.14 + */
    4.15 +
    4.16 +#ifndef _GLCDDRIVERS_PICCTL_H_
    4.17 +#define _GLCDDRIVERS_PICCTL_H_
    4.18 +
    4.19 +#include "driver.h"
    4.20 +
    4.21 +namespace GLCD
    4.22 +{
    4.23 +
    4.24 +class cDriverConfig;
    4.25 +class cSerialPort;
    4.26 +
    4.27 +class cDriverPICCtl : public cDriver
    4.28 +{
    4.29 +private:
    4.30 +    cSerialPort * port;
    4.31 +    unsigned char ** newLCD; // wanted state
    4.32 +    unsigned char ** oldLCD; // current state
    4.33 +    cDriverConfig * config;
    4.34 +    cDriverConfig * oldConfig;
    4.35 +    int refreshCounter;
    4.36 +    bool ack_flag;
    4.37 +
    4.38 +    int WaitForAck(void);
    4.39 +    void CmdDispClearScreen(void);
    4.40 +    void CmdSetMode(uint8_t mode);
    4.41 +    void CmdDispSetManaged(void);
    4.42 +    void CmdDispSetUnManaged(void);
    4.43 +    void CmdDispSetBrightness(uint8_t percent);
    4.44 +    void CmdDispSetColData(uint8_t yoffset, uint8_t xoffset, uint8_t length, uint8_t * data);
    4.45 +
    4.46 +    int CheckSetup();
    4.47 +
    4.48 +    static void SignalHandler(int signal);
    4.49 +
    4.50 +// singleton
    4.51 +    static cDriverPICCtl* instance;		// die EINE instant
    4.52 +    cDriverPICCtl(cDriverConfig * config);	// Konstruktor
    4.53 +
    4.54 +public:
    4.55 +    virtual int Init();
    4.56 +    virtual int DeInit();
    4.57 +
    4.58 +    virtual void Clear();
    4.59 +    virtual void Set8Pixels(int x, int y, unsigned char data);
    4.60 +    virtual void Refresh(bool refreshAll = false);
    4.61 +    virtual void SetBrightness(unsigned int percent);
    4.62 +    virtual void SetClock(unsigned int percent);
    4.63 +
    4.64 +// singleton
    4.65 +    virtual ~cDriverPICCtl();			// Destruktor
    4.66 +    static cDriverPICCtl* getInstance(cDriverConfig * config);
    4.67 +};
    4.68 +
    4.69 +} // end of namespace
    4.70 +
    4.71 +#endif
     5.1 --- a/graphlcd-base/glcddrivers/port.c	Wed Feb 06 17:32:55 2008 +0000
     5.2 +++ b/graphlcd-base/glcddrivers/port.c	Wed Feb 06 17:37:50 2008 +0000
     5.3 @@ -16,6 +16,7 @@
     5.4  #include <syslog.h>
     5.5  #include <unistd.h>
     5.6  #include <termios.h>
     5.7 +#include <signal.h>
     5.8  #include <sys/io.h>
     5.9  #include <sys/ioctl.h>
    5.10  #include <linux/ppdev.h>
    5.11 @@ -25,6 +26,9 @@
    5.12  
    5.13  #include "port.h"
    5.14  
    5.15 +
    5.16 +
    5.17 +
    5.18  namespace GLCD
    5.19  {
    5.20  
    5.21 @@ -282,9 +286,10 @@
    5.22  {
    5.23  }
    5.24  
    5.25 -int cSerialPort::Open(const char * device)
    5.26 +int cSerialPort::Open(const char * device, void (*FP)(int))
    5.27  {
    5.28      struct termios options;
    5.29 +    struct sigaction saio;
    5.30  
    5.31      fd = open(device, O_RDWR | O_NOCTTY | O_NDELAY);
    5.32      if (fd == -1)
    5.33 @@ -292,8 +297,19 @@
    5.34          printf("error opening port\n");
    5.35          return -1;
    5.36      }
    5.37 -    //fcntl(fd, F_SETFL, FNDELAY);
    5.38 -    fcntl(fd, F_SETFL, 0);
    5.39 +
    5.40 +
    5.41 +    // install the signal handler before making the device asynchronous/
    5.42 +    saio.sa_handler = FP;
    5.43 +    sigemptyset (&saio.sa_mask);
    5.44 +    saio.sa_flags = 0;
    5.45 +    saio.sa_restorer = NULL;
    5.46 +    sigaction(SIGIO,&saio,NULL);
    5.47 +    
    5.48 +    // allow the process to receive SIGIO
    5.49 +    fcntl(fd, F_SETOWN, getpid());
    5.50 +    // Make the file descriptor asynchronous 
    5.51 +    fcntl(fd, F_SETFL, FASYNC);
    5.52  
    5.53      tcgetattr(fd, &options);
    5.54  
    5.55 @@ -328,11 +344,11 @@
    5.56      return 0;
    5.57  }
    5.58  
    5.59 -int cSerialPort::ReadData(unsigned char * data)
    5.60 +int cSerialPort::ReadData(unsigned char * data, int num)
    5.61  {
    5.62      if (fd == -1)
    5.63          return 0;
    5.64 -    return read(fd, data, 1);
    5.65 +    return read(fd, data, num);
    5.66  }
    5.67  
    5.68  void cSerialPort::WriteData(unsigned char data)
    5.69 @@ -347,4 +363,6 @@
    5.70      write(fd, data, length);
    5.71  }
    5.72  
    5.73 +
    5.74  } // end of namespace
    5.75 +
     6.1 --- a/graphlcd-base/glcddrivers/port.h	Wed Feb 06 17:32:55 2008 +0000
     6.2 +++ b/graphlcd-base/glcddrivers/port.h	Wed Feb 06 17:37:50 2008 +0000
     6.3 @@ -65,10 +65,10 @@
     6.4      cSerialPort();
     6.5      ~cSerialPort();
     6.6  
     6.7 -    int Open(const char * device);
     6.8 +    int Open(const char * device, void (*FP)(int));
     6.9      int Close();
    6.10  
    6.11 -    int ReadData(unsigned char * data);
    6.12 +    int ReadData(unsigned char * data, int num);
    6.13      void WriteData(unsigned char data);
    6.14      void WriteData(unsigned char * data, unsigned short length);
    6.15  };