Update i2c driver to have pins defined via config file, rather than hardcoded
This commit is contained in:
@@ -2516,6 +2516,61 @@ Size=40x2
|
||||
DelayBus=false
|
||||
DelayMult=1
|
||||
Keypad=no
|
||||
#i2c_line_RS=0x10
|
||||
#i2c_line_RW=0x20
|
||||
#i2c_line_EN=0x40
|
||||
#i2c_line_BL=0x80
|
||||
#i2c_line_D4=0x01
|
||||
#i2c_line_D5=0x02
|
||||
#i2c_line_D6=0x04
|
||||
#i2c_line_D7=0x08
|
||||
# BacklightInvert=yes
|
||||
# The Backlight Invert is used if a 0 turns the backlight on, and 1 turns it off, i.e. npn transistor
|
||||
]]>
|
||||
</screen>
|
||||
</example>
|
||||
|
||||
<para>
|
||||
If your port expander has different wiring you can re-assign the pins in the config file
|
||||
</para>
|
||||
|
||||
<example id="hd44780-i2c-config.example alternative wiring">
|
||||
<title>HD44780: Configuration for I<superscript>2</superscript>C with port expander
|
||||
Alternative Wiring</title>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
- PCF8574AP: P0 P1 P2 P3 P4 P5 P6 P7
|
||||
- | | | | | | | |
|
||||
- HD44780: RS RW EN BL D4 D5 D6 D7
|
||||
]]>
|
||||
</screen>
|
||||
</example>
|
||||
|
||||
<example id="hd44780-i2c-config.example alternative config">
|
||||
<title>HD44780: Configuration for I<superscript>2</superscript>C with port expander
|
||||
alternative config</title>
|
||||
<screen>
|
||||
<![CDATA[
|
||||
[HD44780]
|
||||
ConnectionType=i2c
|
||||
Device=/dev/i2c-0
|
||||
Port=0x20
|
||||
Size=40x2
|
||||
DelayBus=false
|
||||
DelayMult=1
|
||||
Keypad=no
|
||||
i2c_line_RS=0x01
|
||||
i2c_line_RW=0x02
|
||||
i2c_line_EN=0x04
|
||||
i2c_line_BL=0x80
|
||||
i2c_line_D4=0x10
|
||||
i2c_line_D5=0x20
|
||||
i2c_line_D6=0x40
|
||||
i2c_line_D7=0x80
|
||||
Backlight=yes
|
||||
BacklightInvert=yes
|
||||
#The Backlight Invert is used if a 0 turns the backlight on, and 1 turns it off,
|
||||
i.e. npn transistor
|
||||
]]>
|
||||
</screen>
|
||||
</example>
|
||||
|
||||
@@ -13,17 +13,38 @@
|
||||
* 1997 Matthias Prinke <m.prinke@trashcan.mcnet.de>
|
||||
*
|
||||
* The connections are:
|
||||
* PCF8574AP LCD
|
||||
* P0 (4) D4 (11)
|
||||
* P1 (5) D5 (12)
|
||||
* P2 (6) D6 (13)
|
||||
* P3 (7) D7 (14)
|
||||
* P4 (9) RS (4)
|
||||
* P5 (10) RW (5)
|
||||
* P6 (11) EN (6)
|
||||
* PCF8574AP Bit LCD
|
||||
* P0 (4) 0x01 D4 (11)
|
||||
* P1 (5) 0x02 D5 (12)
|
||||
* P2 (6) 0x04 D6 (13)
|
||||
* P3 (7) 0x08 D7 (14)
|
||||
* P4 (9) 0x10 RS (4)
|
||||
* P5 (10) 0x20 RW (5)
|
||||
* P6 (11) 0x40 EN (6)
|
||||
* P7 (12) 0x80 /backlight (optional, active-low)
|
||||
*
|
||||
* Backlight
|
||||
* P7 (12) /backlight (optional, active-low)
|
||||
* Configuration:
|
||||
\verbatim
|
||||
alternative wiring example:
|
||||
PCF8574AP: P0 P1 P2 P3 P4 P5 P6 P7
|
||||
| | | | | | | |
|
||||
HD44780: RS RW EN BL D4 D5 D6 D7
|
||||
|
||||
in LCDd.conf we then need to define
|
||||
i2c_line_RS=0x01
|
||||
i2c_line_RW=0x02
|
||||
i2c_line_EN=0x04
|
||||
i2c_line_BL=0x80
|
||||
i2c_line_D4=0x10
|
||||
i2c_line_D5=0x20
|
||||
i2c_line_D6=0x40
|
||||
i2c_line_D7=0x80
|
||||
Backlight=yes
|
||||
BacklightInvert=yes
|
||||
|
||||
The Backlight Invert is used if a 0 turns the backlight on, and 1 turns it off, i.e. npn transistor
|
||||
\endverbatim
|
||||
|
||||
*
|
||||
* Configuration:
|
||||
* device=/dev/i2c-0 # the device file of the i2c bus
|
||||
@@ -89,6 +110,11 @@ void i2c_HD44780_close(PrivateData *p);
|
||||
#define RW 0x20
|
||||
#define EN 0x40
|
||||
#define BL 0x80
|
||||
#define D4 0x01
|
||||
#define D5 0x02
|
||||
#define D6 0x04
|
||||
#define D7 0x08
|
||||
#define BL_INVERT 0
|
||||
// note that the above bits are all meant for the data port of PCF8574
|
||||
|
||||
#define I2C_ADDR_MASK 0x7f
|
||||
@@ -145,14 +171,34 @@ hd_init_i2c(Driver *drvthis)
|
||||
PrivateData *p = (PrivateData*) drvthis->private_data;
|
||||
HD44780_functions *hd44780_functions = p->hd44780_functions;
|
||||
|
||||
int enableLines = EN;
|
||||
char device[256] = DEFAULT_DEVICE;
|
||||
p->i2c_backlight_invert = drvthis->config_get_bool(drvthis->name, "BacklightInvert", 0, BL_INVERT);
|
||||
p->i2c_line_RS = drvthis->config_get_int(drvthis->name, "i2c_line_RS", 0, RS);
|
||||
p->i2c_line_RW = drvthis->config_get_int(drvthis->name, "i2c_line_RW", 0, RW);
|
||||
p->i2c_line_EN = drvthis->config_get_int(drvthis->name, "i2c_line_EN", 0, EN);
|
||||
p->i2c_line_BL = drvthis->config_get_int(drvthis->name, "i2c_line_BL", 0, BL);
|
||||
p->i2c_line_D4 = drvthis->config_get_int(drvthis->name, "i2c_line_D4", 0, D4);
|
||||
p->i2c_line_D5 = drvthis->config_get_int(drvthis->name, "i2c_line_D5", 0, D5);
|
||||
p->i2c_line_D6 = drvthis->config_get_int(drvthis->name, "i2c_line_D6", 0, D6);
|
||||
p->i2c_line_D7 = drvthis->config_get_int(drvthis->name, "i2c_line_D7", 0, D7);
|
||||
|
||||
report(RPT_INFO, "HD44780: I2C: Init using D4 and D5, and or'd lines, invert", p->i2c_line_RS);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin RS mapped to 0x%02X", p->i2c_line_RS);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin RW mapped to 0x%02X", p->i2c_line_RW);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin EN mapped to 0x%02X", p->i2c_line_EN);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin BL mapped to 0x%02X", p->i2c_line_BL);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin D4 mapped to 0x%02X", p->i2c_line_D4);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin D5 mapped to 0x%02X", p->i2c_line_D5);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin D6 mapped to 0x%02X", p->i2c_line_D6);
|
||||
report(RPT_INFO, "HD44780: I2C: Pin D7 mapped to 0x%02X", p->i2c_line_D7);
|
||||
report(RPT_INFO, "HD44780: I2C: Invert Backlight %d", p->i2c_backlight_invert);
|
||||
|
||||
char device[256] = DEFAULT_DEVICE;
|
||||
#ifdef HAVE_DEV_IICBUS_IIC_H
|
||||
struct iiccmd cmd;
|
||||
bzero(&cmd, sizeof(cmd));
|
||||
#endif
|
||||
|
||||
p->backlight_bit = BL;
|
||||
p->backlight_bit = p->i2c_line_BL;
|
||||
|
||||
/* READ CONFIG FILE */
|
||||
|
||||
@@ -209,44 +255,49 @@ hd_init_i2c(Driver *drvthis)
|
||||
|
||||
// powerup the lcd now
|
||||
/* We'll now send 0x03 a couple of times,
|
||||
* which is in fact (FUNCSET | IF_8BIT) >> 4 */
|
||||
i2c_out(p, 0x03);
|
||||
* which is in fact (FUNCSET | IF_8BIT) >> 4
|
||||
*/
|
||||
i2c_out(p, p->i2c_line_D4 | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
|
||||
i2c_out(p, enableLines | 0x03);
|
||||
i2c_out(p, p->i2c_line_EN | p->i2c_line_D4 | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, 0x03);
|
||||
i2c_out(p, p->i2c_line_D4 | p->i2c_line_D5);
|
||||
hd44780_functions->uPause(p, 15000);
|
||||
|
||||
i2c_out(p, enableLines | 0x03);
|
||||
i2c_out(p, p->i2c_line_EN | p->i2c_line_D4 | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, 0x03);
|
||||
i2c_out(p, p->i2c_line_D4 | p->i2c_line_D5);
|
||||
hd44780_functions->uPause(p, 5000);
|
||||
|
||||
i2c_out(p, enableLines | 0x03);
|
||||
i2c_out(p, p->i2c_line_EN | p->i2c_line_D4 | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, 0x03);
|
||||
i2c_out(p, p->i2c_line_D4 | p->i2c_line_D5);
|
||||
hd44780_functions->uPause(p, 100);
|
||||
|
||||
i2c_out(p, enableLines | 0x03);
|
||||
i2c_out(p, p->i2c_line_EN | p->i2c_line_D4 | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, 0x03);
|
||||
i2c_out(p, p->i2c_line_D4 | p->i2c_line_D5);
|
||||
hd44780_functions->uPause(p, 100);
|
||||
|
||||
// now in 8-bit mode... set 4-bit mode
|
||||
i2c_out(p, 0x02);
|
||||
/*
|
||||
OLD (FUNCSET | IF_4BIT) >> 4 0x02
|
||||
ALT (FUNCSET | IF_4BIT) 0x20
|
||||
*/
|
||||
i2c_out(p, p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
|
||||
i2c_out(p, enableLines | 0x02);
|
||||
i2c_out(p, p->i2c_line_EN | p->i2c_line_D5);
|
||||
if (p->delayBus)
|
||||
hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, 0x02);
|
||||
i2c_out(p, p->i2c_line_D5);
|
||||
hd44780_functions->uPause(p, 100);
|
||||
|
||||
// Set up two-line, small character (5x8) mode
|
||||
@@ -279,23 +330,28 @@ i2c_HD44780_close(PrivateData *p) {
|
||||
void
|
||||
i2c_HD44780_senddata(PrivateData *p, unsigned char displayID, unsigned char flags, unsigned char ch)
|
||||
{
|
||||
unsigned char enableLines = 0, portControl = 0;
|
||||
unsigned char h = (ch >> 4) & 0x0f; // high and low nibbles
|
||||
unsigned char l = ch & 0x0f;
|
||||
|
||||
unsigned char portControl = 0;
|
||||
unsigned char h=0;
|
||||
unsigned char l=0;
|
||||
if( ch & 0x80 ) h |= p->i2c_line_D7;
|
||||
if( ch & 0x40 ) h |= p->i2c_line_D6;
|
||||
if( ch & 0x20 ) h |= p->i2c_line_D5;
|
||||
if( ch & 0x10 ) h |= p->i2c_line_D4;
|
||||
if( ch & 0x08 ) l |= p->i2c_line_D7;
|
||||
if( ch & 0x04 ) l |= p->i2c_line_D6;
|
||||
if( ch & 0x02 ) l |= p->i2c_line_D5;
|
||||
if( ch & 0x01 ) l |= p->i2c_line_D4;
|
||||
if (flags == RS_INSTR)
|
||||
portControl = 0;
|
||||
else //if (flags == RS_DATA)
|
||||
portControl = RS;
|
||||
portControl = p->i2c_line_RS;
|
||||
|
||||
portControl |= p->backlight_bit;
|
||||
|
||||
enableLines = EN;
|
||||
|
||||
i2c_out(p, portControl | h);
|
||||
if (p->delayBus)
|
||||
p->hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, enableLines | portControl | h);
|
||||
i2c_out(p, p->i2c_line_EN | portControl | h);
|
||||
if (p->delayBus)
|
||||
p->hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, portControl | h);
|
||||
@@ -303,7 +359,7 @@ i2c_HD44780_senddata(PrivateData *p, unsigned char displayID, unsigned char flag
|
||||
i2c_out(p, portControl | l);
|
||||
if (p->delayBus)
|
||||
p->hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, enableLines | portControl | l);
|
||||
i2c_out(p, p->i2c_line_EN | portControl | l);
|
||||
if (p->delayBus)
|
||||
p->hd44780_functions->uPause(p, 1);
|
||||
i2c_out(p, portControl | l);
|
||||
@@ -317,7 +373,9 @@ i2c_HD44780_senddata(PrivateData *p, unsigned char displayID, unsigned char flag
|
||||
*/
|
||||
void i2c_HD44780_backlight(PrivateData *p, unsigned char state)
|
||||
{
|
||||
p->backlight_bit = ((!p->have_backlight||state) ? 0 : BL);
|
||||
|
||||
if ( p->i2c_backlight_invert == 0 )
|
||||
p->backlight_bit = ((!p->have_backlight||state) ? 0 : p->i2c_line_BL);
|
||||
else // Inverted backlight - npn transistor
|
||||
p->backlight_bit = ((p->have_backlight && state) ? p->i2c_line_BL : 0);
|
||||
i2c_out(p, p->backlight_bit);
|
||||
}
|
||||
|
||||
@@ -155,6 +155,21 @@ typedef struct hd44780_private_data {
|
||||
int ftdi_line_backlight;
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_I2C
|
||||
/* libi2c-based connection types */
|
||||
|
||||
int i2c_backlight_invert;
|
||||
int i2c_line_RS;
|
||||
int i2c_line_RW;
|
||||
int i2c_line_EN;
|
||||
int i2c_line_BL;
|
||||
int i2c_line_D4;
|
||||
int i2c_line_D5;
|
||||
int i2c_line_D6;
|
||||
int i2c_line_D7;
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef WITH_ETHLCD
|
||||
int sock; /**< socket for TCP devices */
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user