• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2023 The Pigweed Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
5 // the License at
6 //
7 //     https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
13 // the License.
14 
15 #pragma once
16 
17 #include "fsl_flexio_spi.h"
18 #include "pw_digital_io/digital_io.h"
19 #include "pw_spi/chip_selector.h"
20 #include "pw_spi/initiator.h"
21 #include "pw_status/status.h"
22 #include "pw_sync/binary_semaphore.h"
23 #include "pw_sync/lock_annotations.h"
24 #include "pw_sync/mutex.h"
25 
26 namespace pw::spi {
27 
28 // Mcuxpresso SDK implementation of the FLEXIO SPI Initiator
29 class McuxpressoFlexIoInitiator : public Initiator {
30  public:
31   McuxpressoFlexIoInitiator(FLEXIO_SPI_Type flexio_spi_config,
32                             uint32_t src_clock_hz,
33                             uint32_t baud_rate_bps,
34                             bool blocking = true)
flexio_spi_config_(flexio_spi_config)35       : flexio_spi_config_(flexio_spi_config),
36         src_clock_hz_(src_clock_hz),
37         baud_rate_bps_(baud_rate_bps),
38         blocking_(blocking) {}
39   ~McuxpressoFlexIoInitiator();
40 
41   // Implements pw::spi::Initiator
42   pw::Status Configure(const Config& config) PW_LOCKS_EXCLUDED(mutex_) override;
43   pw::Status WriteRead(ConstByteSpan write_buffer, ByteSpan read_buffer)
44       PW_LOCKS_EXCLUDED(mutex_) override;
45 
46  private:
47   // inclusive-language: disable
48   static void SpiCallback(FLEXIO_SPI_Type*,
49                           flexio_spi_master_handle_t*,
50                           status_t status,
51                           void* context);
52   // Add support to FLEXIO_SPI for negative clock polarity.
53   void ConfigureClock(flexio_spi_master_config_t* masterConfig,
54                       ClockPolarity clockPolarity);
55 
is_initialized()56   bool is_initialized() { return !!current_config_; }
57 
58   std::optional<const Config> current_config_;
59   FLEXIO_SPI_Type flexio_spi_config_;
60   flexio_spi_master_handle_t driver_handle_;
61   // inclusive-language: enable
62   sync::BinarySemaphore transfer_semaphore_;
63   sync::Mutex mutex_;
64   Status last_transfer_status_;
65   uint32_t src_clock_hz_;
66   uint32_t baud_rate_bps_;
67   bool blocking_;
68   uint8_t transfer_flags_;
69 };
70 
71 // Mcuxpresso userspace implementation of SPI ChipSelector. Implemented using
72 // GPIO so as to support manual control of chip select. GPIO pin passed in
73 // should be already initialized and ungated.
74 class McuxpressoFlexIoChipSelector : public ChipSelector {
75  public:
McuxpressoFlexIoChipSelector(digital_io::DigitalOut & pin)76   explicit McuxpressoFlexIoChipSelector(digital_io::DigitalOut& pin)
77       : pin_(pin) {}
78 
79   // Implements pw::spi::ChipSelector
80   pw::Status SetActive(bool active) override;
81 
82  private:
83   digital_io::DigitalOut& pin_;
84 };
85 
86 }  // namespace pw::spi
87