/** \param[in] busNumber The number of the SPI bus to open (0 or 1) \param[in] mode The SPI mode (clock polarity and phase: 0, 1, 2 or 3) \param[in] clockKhz The clock speed to use for the SPI bus \param[in] dataBits The size of an SPI transfer in bits \return HRESULT success or error code. */ HRESULT QuarkSpiControllerClass::begin(ULONG busNumber, ULONG mode, ULONG clockKhz, ULONG dataBits) { HRESULT hr = S_OK; PWCHAR deviceName = nullptr; PVOID baseAddress = nullptr; // If this object does not yet have the SPI bus open: if (m_hController == INVALID_HANDLE_VALUE) { // Get the name of the PCI device that describes the SPI controller. switch (busNumber) { case ADC_SPI_BUS: deviceName = galileoSpi0DeviceName; break; case EXTERNAL_SPI_BUS: deviceName = galileoSpi1DeviceName; break; default: // Only support the two SPI busses hr = DMAP_E_SPI_BUS_REQUESTED_DOES_NOT_EXIST; } if (SUCCEEDED(hr)) { // Open the Dmap device for the SPI controller. hr = GetControllerBaseAddress(deviceName, m_hController, baseAddress); if (SUCCEEDED(hr)) { m_registers = (PSPI_CONTROLLER)baseAddress; } } if (SUCCEEDED(hr)) { // We now "own" the SPI controller, intialize it. m_registers->SSCR0.ALL_BITS = 0; // Disable controller (and also clear other bits) m_registers->SSCR0.DSS = dataBits - 1; // Use the specified data width m_registers->SSCR1.ALL_BITS = 0; // Clear all register bits m_registers->SSSR.ROR = 1; // Clear any RX Overrun Status bit currently set hr = setMode(mode); } if (SUCCEEDED(hr)) { hr = setClock(clockKhz); } } return hr; }
/** \return HRESULT success or error code. */ HRESULT BtFabricGpioControllerClass::_mapS0Controller() { HRESULT hr = S_OK; PVOID baseAddress = nullptr; hr = GetControllerBaseAddress( mbmGpioS0DeviceName, m_hS0Controller, baseAddress, FILE_SHARE_READ | FILE_SHARE_WRITE); if (SUCCEEDED(hr)) { m_s0Controller = (PGPIO_PAD)baseAddress; } return hr; }
/** \return HRESULT error or success code. */ HRESULT QuarkFabricGpioControllerClass::_mapController() { HRESULT hr = S_OK; PVOID baseAddress = nullptr; hr = GetControllerBaseAddress( galileoGpioDeviceName, m_hController, baseAddress, FILE_SHARE_READ | FILE_SHARE_WRITE); if (SUCCEEDED(hr)) { m_controller = (PFABRIC_GPIO)baseAddress; } return hr; }
/** \return HRESULT success or error code. */ HRESULT BcmGpioControllerClass::_mapController() { HRESULT hr = S_OK; PVOID baseAddress = nullptr; hr = GetControllerBaseAddress( pi2GpioDeviceName, m_hController, baseAddress, FILE_SHARE_READ | FILE_SHARE_WRITE); if (SUCCEEDED(hr)) { m_controller = (PBCM_GPIO)baseAddress; } return hr; }
// Method to map the I2C controller into this process' virtual address space. HRESULT BtI2cControllerClass::_mapController() { HRESULT hr = S_OK; PVOID baseAddress = nullptr; BoardPinsClass::BOARD_TYPE board; PWCHAR deviceName = nullptr; hr = g_pins.getBoardType(board); if (SUCCEEDED(hr)) { switch (board) { case BoardPinsClass::BOARD_TYPE::GALILEO_GEN1: case BoardPinsClass::BOARD_TYPE::GALILEO_GEN2: deviceName = galileoI2cDeviceName; break; case BoardPinsClass::BOARD_TYPE::MBM_BARE: case BoardPinsClass::BOARD_TYPE::MBM_IKA_LURE: deviceName = mbmI2cDeviceName; break; default: hr = DMAP_E_BOARD_TYPE_NOT_RECOGNIZED; } } if (SUCCEEDED(hr)) { hr = GetControllerBaseAddress(deviceName, m_hController, baseAddress, FILE_SHARE_READ | FILE_SHARE_WRITE); if (SUCCEEDED(hr)) { m_registers = (PI2C_CONTROLLER)baseAddress; } } return hr; }
/** \return TRUE success, FALSE failure, GetLastError() provides the error code. */ BOOL FabricGpioControllerClass::_mapController() { BOOL status = TRUE; BOOL error = ERROR_SUCCESS; PVOID baseAddress = nullptr; status = GetControllerBaseAddress( dmapGpioDeviceName, m_hController, baseAddress, FILE_SHARE_READ | FILE_SHARE_WRITE); if (!status) { error = GetLastError(); } else { m_controller = (PFABRIC_GPIO)baseAddress; } if (!status) { SetLastError(error); } return status; }
/** \param[in] busNumber The number of the SPI bus to open (0 or 1) \param[in] mode The SPI mode (clock polarity and phase: 0, 1, 2 or 3) \param[in] clockKhz The clock speed to use for the SPI bus \param[in] dataBits The size of an SPI transfer in bits \return HRESULT success or error code. */ HRESULT BcmSpiControllerClass::begin(ULONG busNumber, ULONG mode, ULONG clockKhz, ULONG dataBits) { HRESULT hr = S_OK; PWCHAR deviceName = nullptr; PVOID baseAddress = nullptr; _CS cs; // If this object does not yet have the SPI bus open: if (m_hController == INVALID_HANDLE_VALUE) { // Get the name of the PCI device that describes the SPI controller. switch (busNumber) { case EXTERNAL_SPI_BUS: deviceName = pi2Spi0DeviceName; break; case SECOND_EXTERNAL_SPI_BUS: deviceName = pi2Spi1DeviceName; break; default: // Only support two SPI buses hr = DMAP_E_SPI_BUS_REQUESTED_DOES_NOT_EXIST; } if (SUCCEEDED(hr)) { // Open the Dmap device for the SPI controller for exclusive access. hr = GetControllerBaseAddress(deviceName, m_hController, baseAddress); if (SUCCEEDED(hr)) { m_registers = (PSPI_CONTROLLER)baseAddress; } } // // We now "own" the SPI controller, intialize it. // if (SUCCEEDED(hr)) { hr = setClock(clockKhz); } if (SUCCEEDED(hr)) { hr = setMode(mode); } if (SUCCEEDED(hr)) { cs.ALL_BITS = 0; cs.CPHA = m_clockPhase; cs.CPOL = m_clockPolarity; cs.CLEAR = 3; // Clear both FIFOs, cs.TA = 1; // then start transfers. m_registers->CS.ALL_BITS = cs.ALL_BITS; } } return hr; }
/** \param[in] busNumber The number of the SPI bus to open (0 or 1) \param[in] mode The SPI mode (clock polarity and phase: 0, 1, 2 or 3) \param[in] clockKhz The clock speed to use for the SPI bus \param[in] dataBits The size of an SPI transfer in bits \return HRESULT success or error code. */ HRESULT BtSpiControllerClass::begin(ULONG busNumber, ULONG mode, ULONG clockKhz, ULONG dataBits) { HRESULT hr = S_OK; PWCHAR deviceName = nullptr; PVOID baseAddress = nullptr; _SSCR0 sscr0; _SSSR sssr; // If this object does not yet have the SPI bus open: if (m_hController == INVALID_HANDLE_VALUE) { // Get the name of the PCI device that describes the SPI controller. switch (busNumber) { case EXTERNAL_SPI_BUS: deviceName = mbmSpiDeviceName; break; default: // Only support one SPI bus hr = DMAP_E_SPI_BUS_REQUESTED_DOES_NOT_EXIST; } if (SUCCEEDED(hr)) { // Open the Dmap device for the SPI controller. hr = GetControllerBaseAddress(deviceName, m_hController, baseAddress); if (SUCCEEDED(hr)) { m_registers = (PSPI_CONTROLLER)baseAddress; m_registersUpper = (PSPI_CONTROLLER_UPPER)(((PBYTE)baseAddress) + SPI_CONTROLLER_UPPER_OFFSET); } } if (SUCCEEDED(hr)) { // We now "own" the SPI controller, intialize it. sscr0.ALL_BITS = 0; m_registers->SSCR0.ALL_BITS = sscr0.ALL_BITS; // Disable controller sscr0.DSS = (dataBits - 1) & 0x0F; // Data width ls4bits sscr0.EDSS = ((dataBits - 1) >> 4) & 0x01; // Data width msbit sscr0.RIM = 1; // Mask RX FIFO Over Run interrupts sscr0.TIM = 1; // Mask TX FIFO Under Run interrupts m_registers->SSCR0.ALL_BITS = sscr0.ALL_BITS; m_registers->SSCR1.ALL_BITS = 0; // Master mode, interrupts disabled sssr.ALL_BITS = 0; sssr.ROR = 1; // Clear any Receive Overrun int sssr.PINT = 1; // Clear any Peripheral Trailing Byte int sssr.TINT = 1; // Clear any Receive Time-out int sssr.EOC = 1; // Clear any End of Chain int sssr.TUR = 1; // Clear any Transmit FIFO Under Run int sssr.BCE = 1; // Clear any Bit Count Error m_registers->SSSR.ALL_BITS = sssr.ALL_BITS; hr = setMode(mode); } if (SUCCEEDED(hr)) { hr = setClock(clockKhz); } } return hr; }
/** Get the base address of a memory mapped controller in the SOC. Exclusive, non-shared access to the controller is requested. \param[in] deviceName The name of the PCI device used to map the controller in question. \param[out] handle Handle opened to the device specified by deviceName. \param[out] baseAddress Base address of the controller in question. \return TRUE success, FALSE failure, GetLastError() provides the error code. */ BOOL GetControllerBaseAddress(PWCHAR deviceName, HANDLE & handle, PVOID & baseAddress) { return GetControllerBaseAddress(deviceName, handle, baseAddress, 0); }