i2cdevice.bmx 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248
  1. ' Copyright (c) .NET Foundation and Contributors
  2. ' Copyright (c) 2019 Bruce A Henderson
  3. '
  4. ' All rights reserved.
  5. '
  6. ' Permission is hereby granted, free of charge, to any person obtaining a copy
  7. ' of this software and associated documentation files (the "Software"), to deal
  8. ' in the Software without restriction, including without limitation the rights
  9. ' to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  10. ' copies of the Software, and to permit persons to whom the Software is
  11. ' furnished to do so, subject to the following conditions:
  12. '
  13. ' The above copyright notice and this permission notice shall be included in all
  14. ' copies or substantial portions of the Software.
  15. '
  16. ' THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  17. ' IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  18. ' FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  19. ' AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  20. ' LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  21. ' OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  22. ' SOFTWARE.
  23. '
  24. SuperStrict
  25. Import brl.threads
  26. Import "../../common.bmx"
  27. Rem
  28. bbdoc: The communications channel to a device on an I2C bus.
  29. End Rem
  30. Type TI2cDevice Implements IDisposable
  31. Const DEFAULT_DEVICE_PATH:String = "/dev/i2c"
  32. Field ReadOnly settings:TI2cConnectionSettings
  33. Field deviceFileDescriptor:Int = -1
  34. Field functionalities:EI2cFunctionalityFlags
  35. Field devicePath:String
  36. Field initializationLock:TMutex = TMutex.Create()
  37. Method New(settings:TI2cConnectionSettings)
  38. Self.settings = settings
  39. devicePath = DEFAULT_DEVICE_PATH
  40. End Method
  41. Private
  42. Method Initialize()
  43. If deviceFileDescriptor >= 0 Then
  44. Return
  45. End If
  46. Local deviceFileName:String = devicePath + "-" + settings.GetBusId()
  47. Try
  48. initializationLock.Lock()
  49. deviceFileDescriptor = open_(deviceFileName, O_RDWR)
  50. If deviceFileDescriptor < 0 Then
  51. Throw New TIOException("Cannot open I2C device file '" + deviceFileName + "'.")
  52. End If
  53. Local tempFlags:EI2cFunctionalityFlags
  54. Local result:Int = ioctli2_(deviceFileDescriptor, EI2cSettings.I2C_FUNCS.Ordinal(), tempFlags)
  55. If result < 0 Then
  56. functionalities = EI2cFunctionalityFlags.None
  57. Else
  58. functionalities = tempFlags
  59. End If
  60. Finally
  61. initializationLock.Unlock()
  62. End Try
  63. End Method
  64. Method Transfer(writeBuffer:Byte Ptr, writeLength:Size_T, readBuffer:Byte Ptr, readLength:Size_T)
  65. If functionalities & EI2cFunctionalityFlags.I2C_FUNC_I2C Then
  66. ReadWriteInterfaceTransfer(writeBuffer, writeLength, readBuffer, readLength)
  67. Else
  68. FileInterfaceTransfer(writeBuffer, writeLength, readBuffer, readLength)
  69. End If
  70. End Method
  71. Method ReadWriteInterfaceTransfer(writeBuffer:Byte Ptr, writeLength:Size_T, readBuffer:Byte Ptr, readLength:Size_T)
  72. Local messages:i2c_msg[2]
  73. Local messageCount:UInt
  74. If writeBuffer Then
  75. messages[messageCount] = New i2c_msg(Short(settings.GetDeviceAddress()), Short(EI2cMessageFlags.I2C_M_WR), Short(writeLength), writeBuffer)
  76. messageCount :+ 1
  77. End If
  78. If readBuffer Then
  79. messages[messageCount] = New i2c_msg(Short(settings.GetDeviceAddress()), Short(EI2cMessageFlags.I2C_M_RD), Short(readLength), readBuffer)
  80. messageCount :+ 1
  81. End If
  82. Local msgset:i2c_rdwr_ioctl_data = New i2c_rdwr_ioctl_data(messages, messageCount)
  83. Local result:Int = ioctl_(deviceFileDescriptor, EI2cSettings.I2C_RDWR.Ordinal(), msgset)
  84. If result < 0 Then
  85. Throw New TIOException("Error performing I2C data transfer.")
  86. End If
  87. End Method
  88. Method FileInterfaceTransfer(writeBuffer:Byte Ptr, writeLength:Size_T, readBuffer:Byte Ptr, readLength:Size_T)
  89. Local result:Int = ioctli_(deviceFileDescriptor, EI2cSettings.I2C_SLAVE_FORCE.Ordinal(), settings.DeviceAddress)
  90. If result < 0 Then
  91. Throw New TIOException("Error performing I2C data transfer.")
  92. End If
  93. If writeBuffer Then
  94. result = write_(deviceFileDescriptor, writeBuffer, writeLength)
  95. If result < 0 Then
  96. Throw New TIOException("Error performing I2C data transfer.")
  97. End If
  98. End If
  99. If readBuffer Then
  100. result = read_(deviceFileDescriptor, readBuffer, readLength)
  101. If result < 0 Then
  102. Throw New TIOException("Error performing I2C data transfer.")
  103. End If
  104. End If
  105. End Method
  106. Public
  107. Rem
  108. bbdoc: Reads a byte from the I2C device.
  109. End Rem
  110. Method ReadByte:Byte()
  111. Initialize()
  112. Local result:Byte
  113. Transfer(Null, 0, Varptr result, 1)
  114. Return result
  115. End Method
  116. Rem
  117. bbdoc: Reads data from the I2C device.
  118. End Rem
  119. Method Read(buffer:Byte Ptr, length:Size_T)
  120. Initialize()
  121. Transfer(Null, 0, buffer, length)
  122. End Method
  123. Rem
  124. bbdoc: Writes a byte to the I2C device.
  125. End Rem
  126. Method WriteByte(value:Byte)
  127. Initialize()
  128. Transfer(Varptr value, 1, Null, 0)
  129. End Method
  130. Rem
  131. bbdoc: Writes data to the I2C device.
  132. End Rem
  133. Method Write(buffer:Byte Ptr, length:Size_T)
  134. Initialize()
  135. Transfer(buffer, length, Null, 0)
  136. End Method
  137. Rem
  138. bbdoc: Performs an atomic operation to write data to and then read data from the I2C bus on which the device is connected, and sends a restart condition between the write and read operations.
  139. End Rem
  140. Method WriteRead(writeBuffer:Byte Ptr, writeLength:Size_T, readBuffer:Byte Ptr, readLength:Size_T)
  141. Initialize()
  142. Transfer(writeBuffer, writeLength, readBuffer, readLength)
  143. End Method
  144. Rem
  145. bbdoc: Returns the path to I2C resources located on the system.
  146. End Rem
  147. Method GetDevicePath:String()
  148. Return devicePath
  149. End Method
  150. Rem
  151. bbdoc: Sets the path to I2C resources located on the system.
  152. End Rem
  153. Method SetDevicePath(devicePath:String)
  154. Self.devicePath = devicePath
  155. End Method
  156. Rem
  157. bbdoc: Returns the connection settings of a device on an I2C bus.
  158. End Rem
  159. Method GetConnectionSettings:TI2cConnectionSettings()
  160. Return settings
  161. End Method
  162. Method Dispose() Override
  163. If deviceFileDescriptor >= 0 Then
  164. close_(deviceFileDescriptor)
  165. deviceFileDescriptor = -1
  166. End If
  167. End Method
  168. End Type
  169. Rem
  170. bbdoc: The connection settings of a device on an I2C bus.
  171. End Rem
  172. Type TI2cConnectionSettings
  173. Field ReadOnly busId:Int
  174. Field ReadOnly deviceAddress:Int
  175. Rem
  176. bbdoc: Creates a new instance of #TI2cConnectionSettings.
  177. End Rem
  178. Method New(busId:Int, deviceAddress:Int)
  179. Self.busId = busId
  180. Self.deviceAddress = deviceAddress
  181. End Method
  182. Rem
  183. bbdoc: Creates a copy of a #TI2cConnectionSettings.
  184. End Rem
  185. Method New(other:TI2cConnectionSettings)
  186. busId = other.busId
  187. deviceAddress = other.deviceAddress
  188. End Method
  189. Rem
  190. bbdoc: Returns the bus id that the I2C device is connected to.
  191. End Rem
  192. Method GetBusId:Int()
  193. Return busId
  194. End Method
  195. Rem
  196. bbdoc: Returns the bus address of the I2C device.
  197. End Rem
  198. Method GetDeviceAddress:Int()
  199. Return deviceAddress
  200. End Method
  201. End Type