LCD interfacing with PIC16f877A (ambiguity)

Discussion in 'Embedded Systems and Microcontrollers' started by irilias, Aug 18, 2012.

  1. irilias

    Thread Starter New Member

    Jul 3, 2012
    6
    0
    i just have a little problem understanding some lines in CCS C code that i have for a sphygmomanometer project & i'm not sure if i actually wired the pic16f877a (with the LCD) correctly or not ..

    My reasoning was as follows:
    #define lcd_e1 pin_d7 => i wired the "Enable" LCD pin to the pic pin 30 (RD7/PSP7)

    #define lcd_rs1 pin_d6 => i wired the "Register Select" LCD pin to pic pin 29 (RD6/PSP6)

    #define lcd_port output_b => i wired the LCD's Data pins (DB0,DB1,DB2, ... DB7) to the pic's (pin 33,pin34,pin35,...pin40) in order (which represent RB0 to RB7)

    putcmd_lcd(0x38);

    // sending the 0X38 to the LCD means :
    ( Function Set: 8bit, 2Line, 5x7 Dots ) and that's exactly the reason why i wired the whole 8 lines (and not jut 4) because i think we're using the 8 bit mode of operation .

    * these are the lines that i couldn't understand :

    #use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7)
    do i have to wire the pins C6 & C7 ??
    #define lcd_direction set_tris_b
    #define lcd_command set_tris_c
    and the function : lcd_port()

    i did read the CCS C manual but i couldn't figure out what their actual purpose is ?

    i'm new at this so please bear with me (and excuse my poor english,it's not my native language).. any help at all would be much appreciated, Thanks in advance .

    Code :
    Code ( (Unknown Language)):
    1.  
    2. #include<16f877a.h>
    3. #fuses hs,nowdt, noprotect, nolvp
    4. #use delay(clock=10000000)
    5. #include<math.h>
    6. #include<string.h>
    7. #use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7)
    8. #define lcd_e1 pin_d7
    9. #define lcd_rs1 pin_d6
    10. #define lcd_port output_b
    11. #define lcd_direction set_tris_b
    12. #define lcd_command set_tris_c
    13.  
    14. int mmc_init();
    15. int mmc_response(unsigned char response);
    16. int mmc_write_block(unsigned long block_number);
    17.  
    18. void init_lcd();//preparation de pic pour lcd
    19. void putdata_lcd(int valued);
    20. void erase_lcd();
    21. void putcmd_lcd(int valuec);
    22. void goto_lcd(int x, int y);
    23. void put_string_lcd(char v[16]);
    24.  
    25. /* Initialises the MMC into SPI mode and sets block size, returns 0 on success */
    26. ......
    27. /***************/
    28.  
    29. void init_lcd()
    30. {putcmd_lcd(0x38);
    31. delay_ms(6);
    32. putcmd_lcd(0x38);
    33. delay_ms(6);
    34. putcmd_lcd(0x38);
    35. delay_ms(6);
    36. putcmd_lcd(0x01); //reset
    37. delay_ms(6);
    38. putcmd_lcd(0x06); //increment
    39. delay_ms(6);
    40. putcmd_lcd(0x0c);
    41. delay_ms(6);}
    42.  
    43. void putdata_lcd(int valued)
    44. {lcd_port(valued);
    45. output_high(lcd_rs1); //data
    46. output_high(lcd_e1);
    47. delay_ms(1);
    48. output_low(lcd_e1);
    49. delay_ms(6);
    50. output_low(lcd_rs1); //command
    51. }
    52.  
    53. void erase_lcd()
    54. {putcmd_lcd(0x01);}
    55.  
    56. void putcmd_lcd(int valuec)
    57. {lcd_port(valuec);
    58. output_low(lcd_rs1);
    59. output_high(lcd_e1);
    60. delay_ms(1);
    61. output_low(lcd_e1);
    62. delay_ms(6);}
    63.  
    64. void goto_lcd(int x, int y)
    65. { if (y==1)
    66. {putcmd_lcd(0x80 + x);}
    67. if (y==2)
    68. {putcmd_lcd(0xc0 + x);}}
    69.  
    70. void put_string_lcd(char v[16])
    71. {long i;
    72. for(i=0;i<=strlen(v);i++)
    73. putdata_lcd(v[i]);}
    74. [/i]
     
  2. BMorse

    Senior Member

    Sep 26, 2009
    2,675
    234



    From what you described with the pin configuration, it seems you have everything wired correctly, as for C6 and C7, apparently the original code included the use of the serial port, this does not need to be connected to the LCD, this is meant to transmit serial data, which was most likely used for debugging purposes by the original author to see data on a PC app such as Hyperterminal or Putty.... if you could post all of the original code I may be able to tell you exactly what it was used for....
     
  3. irilias

    Thread Starter New Member

    Jul 3, 2012
    6
    0
    thank you so much for your quick reply, & what about the #define lcd_direction set_tris_b
    #define lcd_command set_tris_c
    and the function : lcd_port()

    ( i know that "set_tris_b" as a command could set the port B as a PORT OUT or IN ...)

    Thank you again, i really appreciate it
     
  4. takao21203

    Distinguished Member

    Apr 28, 2012
    3,577
    463
    Here some PIC C code that actually works for 4-bit LCD.
     
  5. irilias

    Thread Starter New Member

    Jul 3, 2012
    6
    0
    here's the Original CODE
    Code ( (Unknown Language)):
    1.  
    2. #include<16f877a.h>
    3. #fuses hs,nowdt, noprotect, nolvp
    4. #use delay(clock=10000000)
    5. #include<math.h>
    6. #include<string.h>
    7. #use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7)
    8. #define lcd_e1 pin_d7
    9. #define lcd_rs1 pin_d6
    10. #define lcd_port output_b//b=sortie
    11. #define lcd_direction set_tris_b
    12. #define lcd_command set_tris_c
    13. int mmc_init();
    14. int mmc_response(unsigned char response);
    15. int mmc_write_block(unsigned long block_number);
    16. void init_lcd();//preparation de pic pour lcd
    17. void putdata_lcd(int valued);
    18. void erase_lcd();
    19. void putcmd_lcd(int valuec);
    20. void goto_lcd(int x, int y);
    21. void put_string_lcd(char v[16]);
    22. /**/
    23. /* Initialises the MMC into SPI mode and sets block size, returns 0 on success */
    24.  
    25. int mmc_init()
    26. {
    27. int i;
    28. SETUP_SPI(SPI_MASTER | SPI_H_TO_L | SPI_CLK_DIV_4 | SPI_SS_DISABLED);
    29. *0x94 |= 0x40; // set CKE = 1 - clock idle low
    30. *0x14 &= 0xEF; // set CKP = 0 - data valid on rising edge
    31. OUTPUT_HIGH(PIN_C2); // set SS = 1 (off)
    32. for(i=0;i<10;i++) // initialise the MMC card into SPI mode by sending clks on
    33. {
    34. SPI_WRITE(0xFF);
    35. }
    36. OUTPUT_LOW(PIN_C2); // set SS = 0 (on) tells card to go to spi mode when it receives reset
    37. SPI_WRITE(0x40); // send reset command
    38. SPI_WRITE(0x00); // all the arguments are 0x00 for the reset command
    39. SPI_WRITE(0x00);
    40. SPI_WRITE(0x00);
    41. SPI_WRITE(0x00);
    42. SPI_WRITE(0x95); // precalculated checksum as we are still in MMC mode
    43.  
    44. puts("Sent go to SPI\n\r");
    45.  
    46. if(mmc_response(0x01)==1) return 1; // if = 1 then there was a timeout waiting for 0x01 from the mmc
    47.  
    48. puts("Got response from MMC\n\r");
    49.  
    50. i = 0;
    51. while((i < 255) && (mmc_response(0x00)==1)) // must keep sending command if response
    52. {
    53. SPI_WRITE(0x41); // send mmc command one to bring out of idle state
    54. SPI_WRITE(0x00); // all the arguments are 0x00 for command one
    55. SPI_WRITE(0x00);
    56. SPI_WRITE(0x00);
    57. SPI_WRITE(0x00);
    58. SPI_WRITE(0xFF); // checksum is no longer required but we always send
    59. 0xFF
    60. i++;
    61. }
    62.  
    63. if(i >= 254) return 1; // if >= 254 then there was a timeout waiting for 0x00 from the mmc
    64.  
    65. puts("Got out of idle response from MMC\n\r");
    66.  
    67. OUTPUT_HIGH(PIN_C2); // set SS = 1 (off)
    68. SPI_WRITE(0xFF); // extra clocks to allow mmc to finish off what it is doing
    69. OUTPUT_LOW(PIN_C2); // set SS = 0 (on)
    70. SPI_WRITE(0x50); // send mmc command one to bring out of idle state
    71. SPI_WRITE(0x00);
    72. SPI_WRITE(0x00);
    73. SPI_WRITE(0x02); // high block length bits - 512 bytes
    74. SPI_WRITE(0x00); // low block length bits
    75. SPI_WRITE(0xFF); // checksum is no longer required but we always send 0xFF
    76.  
    77. if((mmc_response(0x00))==1) return 1;
    78.  
    79. OUTPUT_HIGH(PIN_C2); // set SS = 1 (off)
    80. puts("Got set block length response from MMC\n\r");
    81. return 0;
    82. }
    83.  
    84. /************************** MMC Write Block **************************************/
    85. int mmc_write_block(unsigned long block_number)
    86. {
    87. unsigned long i;
    88. unsigned long varh,varl;
    89. char p,f,n;
    90. set_adc_channel(0);
    91. delay_us(10);
    92. f=read_adc();
    93. n=(f*5)/256;
    94. p=(n*9375)/206;
    95. varl=((block_number&0x003F)<<9);
    96. varh=((block_number&0xFFC0)>>7);
    97. puts("Write block\n\r"); // block size has been set in mmc_init()
    98. OUTPUT_LOW(PIN_C2); // set SS = 0 (on)
    99.  
    100. SPI_WRITE(0x58); // send mmc write block
    101. SPI_WRITE(varh);
    102. SPI_WRITE(varl);
    103. SPI_WRITE(0x00); // always zero as mulitples of 512
    104. SPI_WRITE(0xFF); // checksum is no longer required but we always send 0xFF
    105.  
    106. if((mmc_response(0x00))==1) return 1;
    107.  
    108. puts("Got response to write block\n\r");
    109. SPI_WRITE(0xFE); // send data token
    110.  
    111. for(i=0;i<512;i++)
    112. {
    113. SPI_WRITE(p); // send data
    114. }
    115.  
    116. SPI_WRITE(0xFF); // dummy CRC
    117. SPI_WRITE(0xFF);
    118.  
    119. if((SPI_READ(0xFF)&0x0F)!=0x05) return 1;
    120.  
    121. puts("Got data response to write block\n\r");
    122. OUTPUT_HIGH(PIN_C2); // set SS = 1 (off)
    123. return 0;
    124. }
    125.  
    126. /************************** MMC get response **************************************/
    127. /**** Repeatedly reads the MMC until we get the response we want or timeout ****/
    128. int mmc_response(unsigned char response)
    129. {
    130. unsigned long count = 0xFFFF; // 16bit repeat, it may be possible to shrink this to 8 bit but there is not much point
    131.  
    132. while(SPI_READ(0xFF) != response && --count > 0);
    133.  
    134. if(count==0) return 1; // loop was exited due to timeout
    135. else return 0; // loop was exited before timeout
    136. }
    137. /*******************************************************************************************/
    138.  
    139. void init_lcd()
    140.  
    141. {putcmd_lcd(0x38);
    142. delay_ms(6);
    143. putcmd_lcd(0x38);
    144. delay_ms(6);
    145. putcmd_lcd(0x38);
    146. delay_ms(6);
    147. putcmd_lcd(0x01);//reset
    148. delay_ms(6);
    149. putcmd_lcd(0x06);//increment
    150. delay_ms(6);
    151. putcmd_lcd(0x0c);
    152. delay_ms(6);}
    153.  
    154. void putdata_lcd(int valued)
    155.  
    156. {lcd_port(valued);
    157. output_high(lcd_rs1);//data
    158. output_high(lcd_e1);
    159. delay_ms(1);
    160. output_low(lcd_e1);
    161. delay_ms(6);
    162. output_low(lcd_rs1);//command
    163. }
    164.  
    165. void erase_lcd()
    166.  
    167. {putcmd_lcd(0x01);}
    168.  
    169. void putcmd_lcd(int valuec)
    170. {lcd_port(valuec);
    171. output_low(lcd_rs1);
    172. output_high(lcd_e1);
    173. delay_ms(1);
    174. output_low(lcd_e1);
    175. delay_ms(6);}
    176.  
    177. void goto_lcd(int x, int y)
    178. { if (y==1)
    179. {putcmd_lcd(0x80 + x);}
    180. if (y==2)
    181. {putcmd_lcd(0xc0 + x);}}
    182.  
    183. void put_string_lcd(char v[16])
    184.  
    185. {long i;
    186. for(i=0;i<=strlen(v);i++)
    187. putdata_lcd(v[i]);}
    188.  
    189. void print()
    190.  
    191. {char v[16];
    192. init_lcd();
    193. goto_lcd(4,1);
    194. sprintf(v,"Working!");
    195. put_string_lcd(v);
    196. goto_lcd(2,2);
    197. sprintf(v,"Please wait!");
    198. put_string_lcd(v);}
    199.  
    200. void delay()
    201. {delay_ms(500);}
    202.  
    203. void main()
    204.  
    205. {long sy;
    206. float s,f,p,n,m;
    207. char v[16];
    208. sy=0;
    209. mmc_init();
    210. lcd_direction(0x00);
    211. lcd_command(0x00);
    212. set_tris_d(0x00);
    213. setup_adc_ports( all_analog );
    214. setup_adc(ADC_CLOCK_DIV_2);
    215.  
    216. //start deflate
    217.  
    218. start:
    219. set_adc_channel(0);
    220. delay_us(10);
    221.  
    222. s=read_adc();
    223.  
    224. if (s>25){
    225. output_high(pin_d3);
    226. output_low(pin_d2);
    227. goto start;}
    228.  
    229. output_low(pin_d3);
    230. delay_ms(100);
    231. print();
    232. delay_ms(3000);
    233.  
    234. //inflate state
    235.  
    236. init_lcd();
    237. goto_lcd(0,1);
    238. sprintf(v,"pressure=");
    239. put_string_lcd(v);
    240.  
    241. inflate:
    242.  
    243. set_adc_channel(0);
    244. delay_us(10);
    245. f=read_adc();
    246. n=(f*5)/256;
    247. p=(n*9375)/206;
    248. goto_lcd(9,1);
    249. sprintf(v,"%fummHg",p);
    250. put_string_lcd(v);
    251. if (f<178){
    252. output_high(pin_d2);
    253. goto inflate;}
    254. output_low(pin_d2);
    255.  
    256. //deflate state
    257.  
    258. deflate:
    259.  
    260. set_adc_channel(1);
    261. delay_us(10);
    262. s=read_adc();
    263. output_high(pin_d3);
    264. delay_ms(100);
    265. output_low(pin_d3);
    266. delay_ms(100);
    267.  
    268. if (s>205){
    269. sy++;}
    270.  
    271. if (sy<4){
    272. goto deflate;}
    273.  
    274. set_adc_channel(0);
    275. delay_us(10);
    276. f=read_adc();
    277. n=(f*5)/256;
    278. p=(n*9375)/206;
    279. mmc_write_block(1);
    280. init_lcd();
    281. goto_lcd(0,1);
    282. sprintf(v,"Sys pres =");
    283. put_string_lcd(v);
    284. goto_lcd(0,2);
    285. sprintf(v,"%fummHg",p);
    286. put_string_lcd(v);
    287. delay_ms(100);
    288.  
    289. //diastole
    290.  
    291. diastole:
    292.  
    293. output_high(pin_d3);
    294. delay_ms(100);
    295. output_low(pin_d3);
    296. delay_ms(100);
    297. set_adc_channel(1);
    298. delay_us(10);
    299.  
    300. s=read_adc();
    301.  
    302. if (s>128)
    303. {delay();
    304. goto diastole;}
    305. set_adc_channel(0);
    306. delay_us(10);
    307. f=read_adc();
    308. n=(f*5)/256;
    309. m=(n*9375)/206;
    310. mmc_write_block(10);
    311. init_lcd();
    312. goto_lcd(0,1);
    313. sprintf(v,"Diast pres =");
    314. put_string_lcd(v);
    315. set_adc_channel(0);
    316. goto_lcd(0,2);
    317. sprintf(v,"%fummHg",m);
    318. put_string_lcd(v);
    319.  
    320. end:
    321.  
    322. set_adc_channel(0);
    323. delay_us(10);
    324. s=read_adc();
    325.  
    326. if (s>25)
    327. {output_high(pin_d3);
    328. goto end;}
    329. output_low(pin_d3);}
    330. [/i]
     
  6. irilias

    Thread Starter New Member

    Jul 3, 2012
    6
    0
    Thank you for the code man...
     
Loading...