diff options
author | Linus Nielsen Feltzing <linus@haxx.se> | 2006-02-23 15:24:45 +0000 |
---|---|---|
committer | Linus Nielsen Feltzing <linus@haxx.se> | 2006-02-23 15:24:45 +0000 |
commit | 4feb0fca80c291c37c939e8445f846edd2b231bc (patch) | |
tree | 4a1cc04bc704e0bb7ff8d13129c628010138babc /firmware/target | |
parent | 072744b4f4cfaa8c0ceb8e18f43a92dad78da91a (diff) | |
download | rockbox-4feb0fca80c291c37c939e8445f846edd2b231bc.tar.gz rockbox-4feb0fca80c291c37c939e8445f846edd2b231bc.zip |
PCF50606 driver for iAudio X5
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@8809 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'firmware/target')
-rw-r--r-- | firmware/target/coldfire/iaudio/x5/pcf50606-x5.c | 171 |
1 files changed, 171 insertions, 0 deletions
diff --git a/firmware/target/coldfire/iaudio/x5/pcf50606-x5.c b/firmware/target/coldfire/iaudio/x5/pcf50606-x5.c new file mode 100644 index 0000000000..6f81d38a53 --- /dev/null +++ b/firmware/target/coldfire/iaudio/x5/pcf50606-x5.c | |||
@@ -0,0 +1,171 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2006 by Linus Nielsen Feltzing | ||
11 | * | ||
12 | * All files in this archive are subject to the GNU General Public License. | ||
13 | * See the file COPYING in the source tree root for full license agreement. | ||
14 | * | ||
15 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
16 | * KIND, either express or implied. | ||
17 | * | ||
18 | ****************************************************************************/ | ||
19 | #include "config.h" | ||
20 | #include "cpu.h" | ||
21 | #include <stdbool.h> | ||
22 | #include "kernel.h" | ||
23 | #include "system.h" | ||
24 | #include "hwcompat.h" | ||
25 | #include "logf.h" | ||
26 | #include "debug.h" | ||
27 | #include "string.h" | ||
28 | #include "generic_i2c.h" | ||
29 | |||
30 | void pcf50606_sda_output(void) | ||
31 | { | ||
32 | or_l( 0x00001000, &GPIO1_ENABLE); | ||
33 | } | ||
34 | |||
35 | void pcf50606_sda_input(void) | ||
36 | { | ||
37 | and_l(~0x00001000, &GPIO1_ENABLE); | ||
38 | } | ||
39 | |||
40 | void pcf50606_sda_lo(void) | ||
41 | { | ||
42 | and_l(~0x00001000, &GPIO1_OUT); | ||
43 | } | ||
44 | |||
45 | void pcf50606_sda_hi(void) | ||
46 | { | ||
47 | or_l( 0x00001000, &GPIO1_OUT); | ||
48 | } | ||
49 | |||
50 | int pcf50606_sda(void) | ||
51 | { | ||
52 | return 0x00001000 & GPIO1_READ; | ||
53 | } | ||
54 | |||
55 | void pcf50606_scl_output(void) | ||
56 | { | ||
57 | or_l( 0x00000400, &GPIO_ENABLE); | ||
58 | } | ||
59 | |||
60 | void pcf50606_scl_input(void) | ||
61 | { | ||
62 | and_l(~0x00000400, &GPIO_ENABLE); | ||
63 | } | ||
64 | |||
65 | int pcf50606_scl(void) | ||
66 | { | ||
67 | return 0x00000400 & GPIO_READ; | ||
68 | } | ||
69 | |||
70 | void pcf50606_scl_lo(void) | ||
71 | { | ||
72 | and_l(~0x00000400, &GPIO_OUT); | ||
73 | } | ||
74 | |||
75 | void pcf50606_scl_hi(void) | ||
76 | { | ||
77 | pcf50606_scl_input(); | ||
78 | while(!pcf50606_scl()) | ||
79 | { | ||
80 | } | ||
81 | or_l(0x0400, &GPIO_OUT); | ||
82 | pcf50606_scl_output(); | ||
83 | } | ||
84 | |||
85 | void pcf50606_delay(void) | ||
86 | { | ||
87 | do { int _x; for(_x=0;_x<32;_x++);} while(0); | ||
88 | } | ||
89 | |||
90 | struct i2c_interface pcf50606_i2c = { | ||
91 | 0x10, /* Address */ | ||
92 | |||
93 | /* Bit-banged interface definitions */ | ||
94 | pcf50606_scl_hi, /* Drive SCL high, might sleep on clk stretch */ | ||
95 | pcf50606_scl_lo, /* Drive SCL low */ | ||
96 | pcf50606_sda_hi, /* Drive SDA high */ | ||
97 | pcf50606_sda_lo, /* Drive SDA low */ | ||
98 | pcf50606_sda_input, /* Set SDA as input */ | ||
99 | pcf50606_sda_output, /* Set SDA as output */ | ||
100 | pcf50606_scl_input, /* Set SCL as input */ | ||
101 | pcf50606_scl_output, /* Set SCL as output */ | ||
102 | pcf50606_scl, /* Read SCL, returns 0 or nonzero */ | ||
103 | pcf50606_sda, /* Read SDA, returns 0 or nonzero */ | ||
104 | |||
105 | pcf50606_delay, /* START SDA hold time (tHD:SDA) */ | ||
106 | pcf50606_delay, /* SDA hold time (tHD:DAT) */ | ||
107 | pcf50606_delay, /* SDA setup time (tSU:DAT) */ | ||
108 | pcf50606_delay, /* STOP setup time (tSU:STO) */ | ||
109 | pcf50606_delay, /* Rep. START setup time (tSU:STA) */ | ||
110 | pcf50606_delay, /* SCL high period (tHIGH) */ | ||
111 | }; | ||
112 | |||
113 | int pcf50606_read_multiple(int address, unsigned char* buf, int count) | ||
114 | { | ||
115 | return i2c_read_data(0x10, address, buf, count); | ||
116 | } | ||
117 | |||
118 | int pcf50606_read(int address) | ||
119 | { | ||
120 | int ret; | ||
121 | unsigned char c; | ||
122 | |||
123 | ret = pcf50606_read_multiple(address, &c, 1); | ||
124 | if(ret >= 0) | ||
125 | return c; | ||
126 | else | ||
127 | return ret; | ||
128 | } | ||
129 | |||
130 | int pcf50606_write_multiple(int address, const unsigned char* buf, int count) | ||
131 | { | ||
132 | return i2c_write_data(0x10, address, buf, count); | ||
133 | } | ||
134 | |||
135 | int pcf50606_write(int address, unsigned char val) | ||
136 | { | ||
137 | return pcf50606_write_multiple(address, &val, 1); | ||
138 | } | ||
139 | |||
140 | /* These voltages were determined by measuring the output of the PCF50606 | ||
141 | on a running X5, and verified by disassembling the original firmware */ | ||
142 | static void set_voltages(void) | ||
143 | { | ||
144 | static const unsigned char buf[5] = | ||
145 | { | ||
146 | 0xf4, /* IOREGC = 2.9V, ON in all states */ | ||
147 | 0xf0, /* D1REGC = 2.5V, ON in all states */ | ||
148 | 0xf6, /* D2REGC = 3.1V, ON in all states */ | ||
149 | 0xf4, /* D3REGC = 2.9V, ON in all states */ | ||
150 | }; | ||
151 | |||
152 | pcf50606_write_multiple(0x23, buf, 4); | ||
153 | } | ||
154 | |||
155 | void pcf50606_init(void) | ||
156 | { | ||
157 | /* Bit banged I2C */ | ||
158 | or_l(0x00001000, &GPIO1_OUT); | ||
159 | or_l(0x00000400, &GPIO_OUT); | ||
160 | or_l(0x00001000, &GPIO1_ENABLE); | ||
161 | or_l(0x00000400, &GPIO_ENABLE); | ||
162 | or_l(0x00001000, &GPIO1_FUNCTION); | ||
163 | or_l(0x00000400, &GPIO_FUNCTION); | ||
164 | |||
165 | i2c_add_node(&pcf50606_i2c); | ||
166 | |||
167 | set_voltages(); | ||
168 | |||
169 | pcf50606_write(0x35, 0xf1); /* Backlight PWM = 7kHz 8/16 */ | ||
170 | pcf50606_write(0x38, 0x30); /* Backlight ON */ | ||
171 | } | ||