ds18b20.c 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168
  1. #include <linux/kernel.h>
  2. #include <linux/fs.h>
  3. #include <linux/types.h>
  4. #include <linux/slab.h>
  5. #include <linux/ioctl.h>
  6. #include <linux/delay.h>
  7. #include <linux/mutex.h>
  8. #include <linux/gpio.h>
  9. #include <linux/of_gpio.h>
  10. unsigned int gpio_num = 0;
  11. #define DQ_IN gpio_direction_input(gpio_num)
  12. //#define DQ_OUT gpio_direction_output(gpio_num, gpio_get_value(gpio_num))
  13. #define DQ_OUT gpio_direction_output(gpio_num, 1)
  14. #define DQ_H gpio_set_value(gpio_num, 1)
  15. #define DQ_L gpio_set_value(gpio_num, 0)
  16. #define DQ_V gpio_get_value(gpio_num)
  17. //spinlock_t lock;
  18. //#define DEFINE_MUTEX(LOCK)
  19. struct mutex mutex;
  20. //********************************
  21. //功能:ds18b20复位
  22. //********************************
  23. int init_DS18B20(void)
  24. {
  25. unsigned int result;
  26. DQ_OUT;
  27. DQ_L;
  28. udelay(480);
  29. DQ_H;
  30. DQ_IN;
  31. udelay(65);
  32. result = DQ_V;
  33. udelay(240);
  34. //printk("ds18b20 init result %d,%d", result, DQ_V);
  35. udelay(180);
  36. return result;
  37. }
  38. //*************************************
  39. //功能:从ds18b20读一个字节的数据
  40. //*************************************
  41. unsigned char read_char(void)
  42. {
  43. unsigned int i = 0;
  44. unsigned char dat = 0;
  45. // spin_lock(&lock);
  46. for(i=0; i<8; i++) {
  47. DQ_OUT;
  48. DQ_L;
  49. udelay(2);
  50. DQ_IN;
  51. dat >>= 1;
  52. udelay(2);
  53. if (DQ_V)
  54. dat |= 0x80;
  55. udelay(60);
  56. }
  57. //spin_unlock(&lock);
  58. return dat;
  59. }
  60. //*************************************
  61. //功能:向ds18b20写一个字节的数据
  62. //*************************************
  63. void write_char(unsigned char dat)
  64. {
  65. unsigned int i = 0;
  66. //spin_lock(&lock);
  67. DQ_OUT;
  68. for(i=0; i<8; i++)
  69. {
  70. DQ_L;
  71. udelay(2);
  72. if (dat & 0x01)
  73. DQ_H;
  74. else
  75. DQ_L;
  76. udelay(60);
  77. DQ_H;
  78. udelay(2);
  79. dat >>= 1;
  80. }
  81. //spin_unlock(&lock);
  82. }
  83. int initDs18b20(unsigned int gpioNum)
  84. {
  85. gpio_num = gpioNum;
  86. //spin_lock_init(&lock);
  87. mutex_init(&mutex);
  88. return 0;
  89. }
  90. /*读取数据*/
  91. void readDs18b20Data(unsigned char *value)
  92. {
  93. if (sizeof(&value) > 1){
  94. value[0] = 0xff;
  95. value[1] = 0xff;
  96. }
  97. else
  98. {
  99. return;
  100. }
  101. mutex_lock(&mutex);
  102. // local_irq_disable();
  103. if (init_DS18B20())
  104. {
  105. // local_irq_enable();
  106. mutex_unlock(&mutex);
  107. return;
  108. }
  109. write_char(0xCC);
  110. write_char(0x44);
  111. // local_irq_enable();
  112. //mdelay(750);
  113. mdelay(375);
  114. //msleep(750);
  115. // local_irq_disable();
  116. if (init_DS18B20())
  117. {
  118. // local_irq_enable();
  119. mutex_unlock(&mutex);
  120. return;
  121. }
  122. write_char(0xCC);
  123. write_char(0xBE);
  124. value[0] = read_char();
  125. value[1] = read_char();
  126. // local_irq_enable();
  127. mutex_unlock(&mutex);
  128. //printk("%d: TH:%x, TL:%x, c:%x", gpio_num,read_char(),read_char(),read_char());
  129. // mdelay(1);
  130. //init_DS18B20();
  131. //write_char(0xB4);
  132. //DQ_OUT;
  133. //printk("%d: EC:%d", gpio_num,DQ_V);
  134. //write_char(0xCC);
  135. //write_char(0x4E);
  136. //write_char(0x64);
  137. //write_char(0x00);
  138. //write_char(0x5F);
  139. //init_DS18B20();
  140. //write_char(0xCC);
  141. //write_char(0x48);
  142. }
  143. void freeDs18b20(void)
  144. {
  145. gpio_free(gpio_num);
  146. }