ViewVC Help
View File | Revision Log | Show Annotations | Download File | View Changeset | Root Listing
root/truck/DashInterface/Display.cpp
Revision: 29
Committed: 2008-02-27T16:09:18-08:00 (17 years, 3 months ago) by douglas
File size: 5274 byte(s)
Log Message:
Progress!

File Contents

# User Rev Content
1 douglas 26 // Display (Crystalfontz CFA-635 USB LCD)
2 douglas 6 //
3     // Douglas Thrift
4     //
5     // $Id$
6    
7 douglas 28 #include <foreach.hpp>
8    
9 douglas 25 #include <iostream>
10 douglas 6
11 douglas 26 #include <fcntl.h>
12     #include <termios.h>
13 douglas 25
14 douglas 26 #include "Display.hpp"
15 douglas 25
16 douglas 28 extern bool debug;
17    
18 douglas 26 static uint16_t GetCRC(uint8_t *buffer, size_t length)
19 douglas 25 {
20 douglas 26 static const uint16_t table[256] = {
21 douglas 29 0x00000, 0x01189, 0x02312, 0x0329b, 0x04624, 0x057ad, 0x06536, 0x074bf,
22     0x08C48, 0x09DC1, 0x0AF5A, 0x0BED3, 0x0CA6C, 0x0DBE5, 0x0E97E, 0x0F8F7,
23     0x01081, 0x00108, 0x03393, 0x0221a, 0x056a5, 0x0472c, 0x075b7, 0x0643e,
24     0x09CC9, 0x08D40, 0x0BFDB, 0x0AE52, 0x0DAED, 0x0CB64, 0x0F9FF, 0x0E876,
25     0x02102, 0x0308b, 0x00210, 0x01399, 0x06726, 0x076af, 0x04434, 0x055bd,
26     0x0AD4A, 0x0BCC3, 0x08E58, 0x09FD1, 0x0EB6E, 0x0FAE7, 0x0C87C, 0x0D9F5,
27     0x03183, 0x0200a, 0x01291, 0x00318, 0x077a7, 0x0662e, 0x054b5, 0x0453c,
28     0x0BDCB, 0x0AC42, 0x09ED9, 0x08F50, 0x0FBEF, 0x0EA66, 0x0D8FD, 0x0C974,
29     0x04204, 0x0538d, 0x06116, 0x0709f, 0x00420, 0x015a9, 0x02732, 0x036bb,
30     0x0ce4c, 0x0dfc5, 0x0ed5e, 0x0fcd7, 0x08868, 0x099e1, 0x0ab7a, 0x0baf3,
31     0x05285, 0x0430c, 0x07197, 0x0601e, 0x014a1, 0x00528, 0x037b3, 0x0263a,
32     0x0decd, 0x0cf44, 0x0fddf, 0x0ec56, 0x098e9, 0x08960, 0x0bbfb, 0x0aa72,
33     0x06306, 0x0728f, 0x04014, 0x0519d, 0x02522, 0x034ab, 0x00630, 0x017b9,
34     0x0EF4E, 0x0FEC7, 0x0CC5C, 0x0DDD5, 0x0A96A, 0x0B8E3, 0x08A78, 0x09BF1,
35     0x07387, 0x0620e, 0x05095, 0x0411c, 0x035a3, 0x0242a, 0x016b1, 0x00738,
36     0x0FFCF, 0x0EE46, 0x0DCDD, 0x0CD54, 0x0B9EB, 0x0A862, 0x09AF9, 0x08B70,
37     0x08408, 0x09581, 0x0a71a, 0x0b693, 0x0c22c, 0x0d3a5, 0x0e13e, 0x0f0b7,
38     0x00840, 0x019c9, 0x02b52, 0x03adb, 0x04e64, 0x05fed, 0x06d76, 0x07cff,
39     0x09489, 0x08500, 0x0b79b, 0x0a612, 0x0d2ad, 0x0c324, 0x0f1bf, 0x0e036,
40     0x018c1, 0x00948, 0x03bd3, 0x02a5a, 0x05ee5, 0x04f6c, 0x07df7, 0x06c7e,
41     0x0a50a, 0x0b483, 0x08618, 0x09791, 0x0e32e, 0x0f2a7, 0x0c03c, 0x0d1b5,
42     0x02942, 0x038cb, 0x00a50, 0x01bd9, 0x06f66, 0x07eef, 0x04c74, 0x05dfd,
43     0x0b58b, 0x0a402, 0x09699, 0x08710, 0x0f3af, 0x0e226, 0x0d0bd, 0x0c134,
44     0x039C3, 0x0284A, 0x01AD1, 0x00B58, 0x07FE7, 0x06E6E, 0x05CF5, 0x04D7C,
45     0x0c60c, 0x0d785, 0x0e51e, 0x0f497, 0x08028, 0x091a1, 0x0a33a, 0x0b2b3,
46     0x04a44, 0x05bcd, 0x06956, 0x078df, 0x00c60, 0x01de9, 0x02f72, 0x03efb,
47     0x0d68d, 0x0c704, 0x0f59f, 0x0e416, 0x090a9, 0x08120, 0x0b3bb, 0x0a232,
48     0x05AC5, 0x04B4C, 0x079D7, 0x0685E, 0x01CE1, 0x00D68, 0x03FF3, 0x02E7A,
49     0x0e70e, 0x0f687, 0x0c41c, 0x0d595, 0x0a12a, 0x0b0a3, 0x08238, 0x093b1,
50     0x06b46, 0x07acf, 0x04854, 0x059dd, 0x02d62, 0x03ceb, 0x00e70, 0x01ff9,
51     0x0f78f, 0x0e606, 0x0d49d, 0x0c514, 0x0b1ab, 0x0a022, 0x092b9, 0x08330,
52     0x07BC7, 0x06A4E, 0x058D5, 0x0495C, 0x03DE3, 0x02C6A, 0x01EF1, 0x00F78,
53 douglas 26 };
54     register uint16_t crc(0xffff);
55 douglas 25
56 douglas 26 while (length--)
57     crc = (crc >> 8) ^ table[(crc ^ *buffer++) & 0xff];
58 douglas 25
59 douglas 26 return ~crc;
60     }
61 douglas 25
62 douglas 28 Display::Packet::Packet(Display::Packet::Command command, uint8_t length, const uint8_t *data) : command(command), length(length)
63 douglas 26 {
64     if (length > sizeof (this->data))
65     throw;
66 douglas 25
67 douglas 28 ::memcpy(this->data, data, length);
68 douglas 25
69 douglas 26 crc = GetCRC(reinterpret_cast<uint8_t *>(this), length + 2);
70     }
71 douglas 25
72 douglas 26 void operator<<(int fd, const Display::Packet::Packet &packet)
73     {
74     if (packet.length != sizeof (packet.data))
75     ::memcpy(const_cast<uint8_t *>(packet.data) + packet.length, &packet.crc, 2);
76 douglas 25
77 douglas 26 Posix::Write(fd, &packet, packet.length + 4);
78     }
79 douglas 25
80 douglas 26 void operator>>(int fd, Display::Packet::Packet &packet)
81     {
82     Posix::Read(fd, &packet, 2);
83     Posix::Read(fd, packet.data, packet.length);
84     Posix::Read(fd, &packet.crc, 2);
85 douglas 25
86 douglas 28 if (debug)
87     {
88     char *data;
89 douglas 25
90 douglas 28 ::asprintf(&data, "0x%02x %i ", packet.command, packet.length);
91    
92     std::cerr << data << '[' << packet.GetData() << ']' << std::endl;
93    
94     std::free(data);
95     }
96 douglas 25 }
97    
98 douglas 26 Display::Display(const std::string &device) : ucom(Posix::Open(device, O_RDWR | O_NOCTTY))
99 douglas 25 {
100 douglas 26 ::termios state;
101 douglas 25
102 douglas 26 Posix::CheckError(::tcgetattr(ucom, &state));
103     Posix::CheckError(::cfsetospeed(&state, B115200));
104     Posix::CheckError(::cfsetispeed(&state, B115200));
105    
106     state.c_iflag &= ~(IGNBRK | BRKINT | PARMRK | INPCK | ISTRIP | INLCR | IGNCR | ICRNL | IXON | IXOFF);
107     state.c_iflag |= IGNPAR;
108     state.c_oflag &= ~(OPOST | ONLCR | ONOCR | ONLRET);
109     state.c_cflag &= ~(CSIZE | PARENB | PARODD | HUPCL | CRTSCTS);
110     state.c_cflag |= CREAD | CS8 | CSTOPB | CLOCAL;
111     state.c_lflag &= ~(ISIG | ICANON | IEXTEN | ECHO);
112     state.c_lflag |= NOFLSH;
113    
114     Posix::CheckError(::tcsetattr(ucom, TCSANOW, &state));
115 douglas 25 }
116    
117 douglas 29 Display::Packet Display::Communicate_(Display::Packet::Command command, uint8_t length, const uint8_t *data)
118 douglas 25 {
119 douglas 28 Packet packet(command, length, data), response;
120 douglas 25
121 douglas 26 ucom << packet;
122    
123 douglas 28 _forever
124 douglas 26 {
125     ucom >> response;
126 douglas 28
127     if (packet.command | Packet::Response == response.command)
128     return response;
129    
130     switch (response.command)
131     {
132     case Packet::KeyActivity:
133     keyActivity.push(response);
134    
135     break;
136     case Packet::FanSpeedReport:
137     case Packet::TemperatureSensorReport:
138     break;
139     }
140 douglas 26 }
141 douglas 28 }
142 douglas 26
143 douglas 28 bool Display::Ping(const std::string &data)
144     {
145 douglas 29 return data == Communicate<const std::string &>(Packet::PingCommand, data).GetData();
146 douglas 25 }
147 douglas 28
148     std::string Display::Version()
149     {
150     return Communicate(Packet::GetHardwareAndFirmwareVersion).GetData();
151     }
152    
153 douglas 29 void Display::Set(uint8_t column, uint8_t row, const std::string &data)
154 douglas 28 {
155 douglas 29 Communicate<uint8_t, uint8_t, const std::string &>(Packet::SendDataToLCD, column, row, data);
156 douglas 28 }

Properties

Name Value
svn:keywords Id