Advertisement
Guest User

Untitled

a guest
Dec 12th, 2017
62
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 17.96 KB | None | 0 0
  1. library ieee;
  2. use ieee.std_logic_1164.all;
  3. use ieee.numeric_std.all; -- Worlds longest and most stupid oled controller
  4.  
  5. entity OLED_DISPLAY is
  6. Port (
  7. reset_n : in std_logic;
  8. clk_50 : in std_logic;
  9. ascii_valid : in std_logic;
  10. v_ascii_tdata : in std_logic_vector(24 downto 0); -- 8bits of ascii code contaning temp
  11. v_ascii_hdata : in std_logic_vector(23 downto 0); -- 8bits of ascii code contaning humidity
  12. RW : out std_logic; -- Read/Write select signal, R/W=1: Read R/W: =0: Write
  13. Strobe : out std_logic; -- Same as E, name used from the ARM course (Operation enable signal. Falling edge triggered.)
  14. RS : out std_logic; -- Register select signal. RS=0: Command, RS=1: Data
  15. Data_OLED : out std_logic_vector(7 downto 0));
  16. end OLED_DISPLAY;
  17.  
  18. architecture rtl of OLED_DISPLAY is
  19.  
  20. type t_oled_init_state is (S_idle,
  21. S_function_set, -- Function Set: 001110xx
  22. S_display_off, -- Display OFF: 000010xx
  23. S_display_clear, -- Display Clear: 00000001
  24. S_entry_mode_set, -- Entry Mode Set: 00000110
  25. S_home_command, -- Home Command: 00000010
  26. S_display_on, -- Display ON: 000011xx
  27. S_toggle_strobe);
  28.  
  29. type t_text_print_state is (S_idle, -- Prints the static text
  30. S_upper_colon_address,
  31. S_upper_colon_data,
  32. S_lower_colon_address,
  33. S_lower_colon_data,
  34. S_numb_celsius_sign_adress,
  35. S_numb_celsius_sign_data,
  36. S_numb_c_address,
  37. S_numb_c_data,
  38. S_numb_procent_address,
  39. S_numb_procent_data,
  40. S_toggle_strobe);
  41.  
  42. type t_oled_control_state is (S_idle, -- Updates the ascii values
  43. S_temp_address_tens,
  44. S_temp_data_tens,
  45. S_temp_address_ones,
  46. S_temp_data_ones,
  47. S_temp_address_fraction,
  48. S_temp_data_fraction,
  49. S_humid_address_tens,
  50. S_humid_data_tens,
  51. S_humid_address_ones,
  52. S_humid_data_ones,
  53. S_humid_address_fraction,
  54. S_humid_data_fraction,
  55. S_numb_negative_address,
  56. S_numb_negative_data,
  57. S_toggle_strobe);
  58.  
  59. constant c_cnt_delay600us : integer := 30000-1;
  60. constant c_cnt_delay2ms : integer := 100000-1;
  61. constant c_cnt_delayStrobe : integer := 43-1; -- A bit longer E signal then needed
  62. constant c_cnt_delay100ms : integer := 5000000;
  63.  
  64. signal long_counter : integer range 0 to c_cnt_delay100ms;
  65. signal counter : integer range 0 to c_cnt_delay2ms;
  66. signal flag_init_busy : std_logic; -- Flag for "init phase", including the static text printing phase
  67. signal flag_print_start : std_logic; -- Short flag for starting the "print phase"
  68. signal print_state : t_text_print_state;
  69. signal next_print_state : t_text_print_state;
  70. signal next_state : t_oled_init_state;
  71. signal init_state : t_oled_init_state;
  72. signal next_ctr_state : t_oled_control_state;
  73. signal control_state : t_oled_control_state;
  74. signal tick600us : std_logic; -- Mainly used for overview in sim
  75. signal tick2ms : std_logic; -- Mainly used for overview in sim
  76.  
  77. begin
  78.  
  79. p_oled_state : process(clk_50)
  80. begin
  81.  
  82. if rising_edge(clk_50) then
  83.  
  84. tick600us <= '0';
  85. tick2ms <= '0';
  86.  
  87. case init_state is
  88. when S_idle =>
  89.  
  90. if flag_init_busy = '1' then
  91. if counter = c_cnt_delay2ms then
  92. tick2ms <= '1';
  93. counter <= 0;
  94.  
  95. init_state <= S_toggle_strobe;
  96. next_state <= S_function_set;
  97. else
  98. counter <= counter + 1;
  99. end if;
  100. end if;
  101.  
  102. when S_function_set => -- Function Set: Western European font
  103.  
  104. if counter = c_cnt_delay600us then
  105. counter <= 0;
  106. RS <= '0';
  107. RW <= '0';
  108.  
  109. tick600us <= '1';
  110. counter <= 0;
  111.  
  112. Strobe <= '1';
  113. Data_OLED <= "00111001";
  114.  
  115. init_state <= S_toggle_strobe;
  116. next_state <= S_display_off;
  117. else
  118. counter <= counter + 1;
  119. end if;
  120.  
  121. when S_display_off => -- Display OFF: No cursor, no blinking
  122.  
  123. if counter = c_cnt_delay600us then
  124. tick600us <= '1';
  125. counter <= 0;
  126.  
  127. Strobe <= '1';
  128. Data_OLED <= "00001000";
  129.  
  130. init_state <= S_toggle_strobe;
  131. next_state <= S_display_clear;
  132. else
  133. counter <= counter + 1;
  134. end if;
  135.  
  136. when S_display_clear =>
  137.  
  138. if counter = c_cnt_delay600us then
  139. tick600us <= '1';
  140. counter <= 0;
  141.  
  142. Strobe <= '1';
  143. Data_OLED <= "00000001";
  144.  
  145. init_state <= S_toggle_strobe;
  146. next_state <= S_entry_mode_set;
  147. else
  148. counter <= counter + 1;
  149. end if;
  150.  
  151. when S_entry_mode_set =>
  152.  
  153. if counter = c_cnt_delay2ms then
  154. tick2ms <= '1';
  155. counter <= 0;
  156.  
  157. Strobe <= '1';
  158. Data_OLED <= "00000110";
  159.  
  160. init_state <= S_toggle_strobe;
  161. next_state <= S_home_command;
  162. else
  163. counter <= counter + 1;
  164. end if;
  165.  
  166. when S_home_command =>
  167.  
  168. if counter = c_cnt_delay600us then
  169. tick600us <= '1';
  170. counter <= 0;
  171.  
  172. Strobe <= '1';
  173. Data_OLED <= "00000010";
  174.  
  175. init_state <= S_toggle_strobe;
  176. next_state <= S_display_on;
  177. else
  178. counter <= counter + 1;
  179. end if;
  180.  
  181. when S_display_on => -- Display ON: No cursor, no blinking
  182.  
  183. if counter = c_cnt_delay600us then
  184. tick600us <= '1';
  185. counter <= 0;
  186.  
  187. Strobe <= '1';
  188. Data_OLED <= "00001100";
  189. flag_print_start <= '1';
  190.  
  191. init_state <= S_toggle_strobe;
  192. next_state <= S_idle;
  193. else
  194. counter <= counter + 1;
  195. end if;
  196.  
  197. when S_toggle_strobe =>
  198.  
  199. if counter = c_cnt_delayStrobe then
  200. Strobe <= '0';
  201. counter <= 0;
  202. init_state <= next_state;
  203. else
  204. counter <= counter + 1;
  205. end if;
  206.  
  207. when others =>
  208. init_state <= S_idle;
  209. end case;
  210.  
  211. ---------------------------------------------------------------------- Starts printing the "static" chars
  212.  
  213. case print_state is
  214. when S_idle =>
  215.  
  216. if flag_print_start = '1' then
  217. flag_print_start <= '0';
  218. print_state <= S_upper_colon_address;
  219. end if;
  220.  
  221. when S_upper_colon_address =>
  222.  
  223. if counter = c_cnt_delay600us then
  224. tick600us <= '1';
  225. counter <= 0;
  226.  
  227. RS <= '0';
  228. Strobe <= '1';
  229. Data_OLED <= "10000011"; --ADDRESS 03
  230.  
  231. print_state <= S_toggle_strobe;
  232. next_print_state <= S_upper_colon_data;
  233. else
  234. counter <= counter + 1;
  235. end if;
  236.  
  237.  
  238. when S_upper_colon_data =>
  239.  
  240. if counter = c_cnt_delay600us then
  241. tick600us <= '1';
  242. counter <= 0;
  243.  
  244. RS <= '1';
  245. Strobe <= '1';
  246. Data_OLED <= "00101110"; --ASCII code for ","
  247.  
  248. print_state <= S_toggle_strobe;
  249. next_print_state <= S_lower_colon_address;
  250. else
  251. counter <= counter + 1;
  252. end if;
  253.  
  254.  
  255. when S_lower_colon_address =>
  256.  
  257. if counter = c_cnt_delay600us then
  258. tick600us <= '1';
  259. counter <= 0;
  260.  
  261. RS <= '0';
  262. Strobe <= '1';
  263. Data_OLED <= "11000011"; --ADDRESS 03
  264.  
  265. print_state <= S_toggle_strobe;
  266. next_print_state <= S_lower_colon_data;
  267. else
  268. counter <= counter + 1;
  269. end if;
  270.  
  271.  
  272. when S_lower_colon_data =>
  273.  
  274. if counter = c_cnt_delay600us then
  275. tick600us <= '1';
  276. counter <= 0;
  277.  
  278. RS <= '1';
  279. Strobe <= '1';
  280. Data_OLED <= "00101110"; --ASCII code for ","
  281.  
  282. print_state <= S_toggle_strobe;
  283. next_print_state <= S_numb_celsius_sign_adress;
  284. else
  285. counter <= counter + 1;
  286. end if;
  287.  
  288. when S_numb_celsius_sign_adress =>
  289.  
  290. if counter = c_cnt_delay600us then
  291. tick600us <= '1';
  292. counter <= 0;
  293.  
  294. RS <= '0';
  295. Strobe <= '1';
  296. Data_OLED <= "11000101"; --ADDRESS 44
  297.  
  298. print_state <= S_toggle_strobe;
  299. next_print_state <= S_numb_celsius_sign_data;
  300. else
  301. counter <= counter + 1;
  302. end if;
  303.  
  304. when S_numb_celsius_sign_data =>
  305.  
  306. if counter = c_cnt_delay600us then
  307. tick600us <= '1';
  308. counter <= 0;
  309.  
  310. RS <= '1';
  311. Strobe <= '1';
  312. Data_OLED <= "11010010"; --ASCII code for "*"
  313.  
  314. print_state <= S_toggle_strobe;
  315. next_print_state <= S_numb_c_address;
  316. else
  317. counter <= counter + 1;
  318. end if;
  319.  
  320. when S_numb_c_address =>
  321.  
  322. if counter = c_cnt_delay600us then
  323. tick600us <= '1';
  324. counter <= 0;
  325.  
  326. RS <= '0';
  327. Strobe <= '1';
  328. Data_OLED <= "10000101"; --ADDRESS 05
  329.  
  330. print_state <= S_toggle_strobe;
  331. next_print_state <= S_numb_c_data;
  332. else
  333. counter <= counter + 1;
  334. end if;
  335.  
  336.  
  337. when S_numb_c_data =>
  338.  
  339. if counter = c_cnt_delay600us then
  340. tick600us <= '1';
  341. counter <= 0;
  342.  
  343. RS <= '1';
  344. Strobe <= '1';
  345. Data_OLED <= "01000011"; --ASCII code for "C"
  346.  
  347. print_state <= S_toggle_strobe;
  348. next_print_state <= S_numb_procent_address;
  349. else
  350. counter <= counter + 1;
  351. end if;
  352.  
  353.  
  354. when S_numb_procent_address =>
  355.  
  356. if counter = c_cnt_delay600us then
  357. tick600us <= '1';
  358. counter <= 0;
  359.  
  360. RS <= '0';
  361. Strobe <= '1';
  362. Data_OLED <= "11000101"; --ADDRESS 45
  363.  
  364. print_state <= S_toggle_strobe;
  365. next_print_state <= S_numb_procent_data;
  366. else
  367. counter <= counter + 1;
  368. end if;
  369.  
  370. when S_numb_procent_data =>
  371.  
  372. if counter = c_cnt_delay600us then
  373. tick600us <= '1';
  374. counter <= 0;
  375.  
  376. RS <= '1';
  377. Strobe <= '1';
  378. Data_OLED <= "00100101"; --Data for "%" sign
  379. flag_init_busy <= '0';
  380.  
  381. print_state <= S_toggle_strobe;
  382. next_print_state <= S_idle;
  383. else
  384. counter <= counter + 1;
  385. end if;
  386.  
  387. when S_toggle_strobe =>
  388.  
  389. if counter = c_cnt_delayStrobe then
  390. Strobe <= '0';
  391. counter <= 0;
  392. print_state <= next_print_state;
  393. else
  394. counter <= counter + 1;
  395. end if;
  396.  
  397. when others =>
  398. init_state <= S_idle;
  399. end case;
  400.  
  401. ------------------------------------------------------------------- Update state for the humidity and temp data
  402. case control_state is
  403.  
  404. when S_idle =>
  405. if flag_init_busy = '0' then
  406. if long_counter = c_cnt_delay100ms then
  407. control_state <= S_temp_address_tens;
  408. else
  409. long_counter <= long_counter + 1;
  410. end if;
  411. end if;
  412.  
  413. when S_temp_address_tens =>
  414.  
  415. if counter = c_cnt_delay600us then
  416. tick600us <= '1';
  417. counter <= 0;
  418.  
  419. RS <= '0';
  420. Strobe <= '1';
  421. Data_OLED <= "10000001"; --ADDRESS 01 on the oled
  422.  
  423. control_state <= S_toggle_strobe;
  424. next_ctr_state <= S_temp_data_tens;
  425. else
  426. counter <= counter + 1;
  427. end if;
  428.  
  429. when S_temp_data_tens =>
  430.  
  431. if counter = c_cnt_delay600us then
  432. tick600us <= '1';
  433. counter <= 0;
  434.  
  435. if ascii_valid = '1' then
  436. RS <= '1';
  437. Strobe <= '1';
  438. Data_OLED <= v_ascii_tdata(23 downto 16); --Data for the "tens" off the temp data
  439.  
  440. control_state <= S_toggle_strobe;
  441. next_ctr_state <= S_temp_address_ones;
  442. end if;
  443. else
  444. counter <= counter + 1;
  445. end if;
  446.  
  447. when S_temp_address_ones =>
  448.  
  449. if counter = c_cnt_delay600us then
  450. tick600us <= '1';
  451. counter <= 0;
  452.  
  453. RS <= '0';
  454. Strobe <= '1';
  455. Data_OLED <= "10000010"; --ADDRESS 02 on the oled
  456.  
  457. control_state <= S_toggle_strobe;
  458. next_ctr_state <= S_temp_data_ones;
  459. else
  460. counter <= counter + 1;
  461. end if;
  462.  
  463. when S_temp_data_ones =>
  464.  
  465. if counter = c_cnt_delay600us then
  466. tick600us <= '1';
  467. counter <= 0;
  468.  
  469. if ascii_valid = '1' then
  470. RS <= '1';
  471. Strobe <= '1';
  472. Data_OLED <= v_ascii_tdata(15 downto 8); --Data for the "ones" off temp data
  473.  
  474. control_state <= S_toggle_strobe;
  475. next_ctr_state <= S_temp_address_fraction;
  476. end if;
  477. else
  478. counter <= counter + 1;
  479. end if;
  480.  
  481. when S_temp_address_fraction =>
  482.  
  483. if counter = c_cnt_delay600us then
  484. tick600us <= '1';
  485. counter <= 0;
  486.  
  487. RS <= '0';
  488. Strobe <= '1';
  489. Data_OLED <= "10000100"; --ADDRESS 04 on the oled
  490.  
  491. control_state <= S_toggle_strobe;
  492. next_ctr_state <= S_temp_data_fraction;
  493. else
  494. counter <= counter + 1;
  495. end if;
  496.  
  497. when S_temp_data_fraction =>
  498.  
  499. if counter = c_cnt_delay600us then
  500. tick600us <= '1';
  501. counter <= 0;
  502.  
  503. if ascii_valid = '1' then
  504. RS <= '1';
  505. Strobe <= '1';
  506. Data_OLED <= v_ascii_tdata(7 downto 0); --Data for the "fraction" off the temp data
  507.  
  508. control_state <= S_toggle_strobe;
  509. next_ctr_state <= S_humid_address_tens;
  510. end if;
  511. else
  512. counter <= counter + 1;
  513. end if;
  514.  
  515. when S_humid_address_tens =>
  516.  
  517. if counter = c_cnt_delay600us then
  518. tick600us <= '1';
  519. counter <= 0;
  520.  
  521. RS <= '0';
  522. Strobe <= '1';
  523. Data_OLED <= "11000001"; --ADDRESS 41 on the oled
  524.  
  525. control_state <= S_toggle_strobe;
  526. next_ctr_state <= S_humid_data_tens;
  527. else
  528. counter <= counter + 1;
  529. end if;
  530.  
  531. when S_humid_data_tens =>
  532.  
  533. if counter = c_cnt_delay600us then
  534. tick600us <= '1';
  535. counter <= 0;
  536.  
  537. if ascii_valid = '1' then
  538. RS <= '1';
  539. Strobe <= '1';
  540. Data_OLED <= v_ascii_hdata(23 downto 16); --Data for the "tens" off the humidity data
  541.  
  542. control_state <= S_toggle_strobe;
  543. next_ctr_state <= S_humid_address_ones;
  544. end if;
  545. else
  546. counter <= counter + 1;
  547. end if;
  548.  
  549. when S_humid_address_ones =>
  550.  
  551. if counter = c_cnt_delay600us then
  552. tick600us <= '1';
  553. counter <= 0;
  554.  
  555. RS <= '0';
  556. Strobe <= '1';
  557. Data_OLED <= "11000011"; --ADDRESS 43 on the oled
  558.  
  559. control_state <= S_toggle_strobe;
  560. next_ctr_state <= S_humid_data_ones;
  561. else
  562. counter <= counter + 1;
  563. end if;
  564.  
  565. when S_humid_data_ones =>
  566.  
  567. if counter = c_cnt_delay600us then
  568. tick600us <= '1';
  569. counter <= 0;
  570.  
  571. if ascii_valid = '1' then
  572. RS <= '1';
  573. Strobe <= '1';
  574. Data_OLED <= v_ascii_hdata(15 downto 8); --Data for the "ones" off the humidity data
  575.  
  576. control_state <= S_toggle_strobe;
  577. next_ctr_state <= S_humid_address_fraction;
  578. end if;
  579. else
  580. counter <= counter + 1;
  581. end if;
  582.  
  583. when S_humid_address_fraction =>
  584.  
  585. if counter = c_cnt_delay600us then
  586. tick600us <= '1';
  587. counter <= 0;
  588.  
  589. RS <= '0';
  590. Strobe <= '1';
  591. Data_OLED <= "11000100"; --ADDRESS 44 on the oled
  592.  
  593. control_state <= S_toggle_strobe;
  594. next_ctr_state <= S_humid_data_fraction;
  595. else
  596. counter <= counter + 1;
  597. end if;
  598.  
  599. when S_humid_data_fraction =>
  600.  
  601. if counter = c_cnt_delay600us then
  602. tick600us <= '1';
  603. counter <= 0;
  604.  
  605. if ascii_valid = '1' then
  606. RS <= '1';
  607. Strobe <= '1';
  608. Data_OLED <= v_ascii_hdata(7 downto 0); --Data for the "fraction" off the humidity data
  609.  
  610. control_state <= S_toggle_strobe;
  611. next_ctr_state <= S_numb_negative_address;
  612. end if;
  613. else
  614. counter <= counter + 1;
  615. end if;
  616.  
  617. when S_numb_negative_address =>
  618.  
  619. if counter = c_cnt_delay600us then
  620. tick600us <= '1';
  621. counter <= 0;
  622.  
  623. RS <= '0';
  624. Strobe <= '1';
  625. Data_OLED <= "10000000"; --ADDRESS 00 on the oled
  626.  
  627. control_state <= S_toggle_strobe;
  628. next_ctr_state <= S_numb_negative_data;
  629. else
  630. counter <= counter + 1;
  631. end if;
  632.  
  633. when S_numb_negative_data =>
  634.  
  635. if counter = c_cnt_delay600us then
  636. tick600us <= '1';
  637. counter <= 0;
  638.  
  639. if ascii_valid = '1' then
  640. RS <= '1';
  641. Strobe <= '1';
  642. Data_OLED <= "00101101"; --negative sign
  643. else
  644. RS <= '1';
  645. Strobe <= '1';
  646. Data_OLED <= "11111110"; -- empty sign
  647. end if;
  648.  
  649. control_state <= S_toggle_strobe;
  650. next_ctr_state <= S_temp_address_tens;
  651. else
  652. counter <= counter + 1;
  653. end if;
  654.  
  655. when S_toggle_strobe =>
  656.  
  657. if counter = c_cnt_delayStrobe then
  658. Strobe <= '0';
  659. counter <= 0;
  660. control_state <= next_ctr_state;
  661. else
  662. counter <= counter + 1;
  663. end if;
  664.  
  665. when others =>
  666. control_state <= S_idle;
  667.  
  668. end case;
  669. end if;
  670.  
  671. if reset_n = '0' then
  672. Data_OLED <= (others => '0');
  673. RS <= '0';
  674. RW <= '0';
  675. Strobe <= '0';
  676. flag_print_start <= '0';
  677. flag_init_busy <= '1';
  678. print_state <= S_idle;
  679. control_state <= S_idle;
  680. init_state <= S_idle;
  681. end if;
  682.  
  683. end process p_oled_state;
  684. end architecture rtl;
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement