2024-10-18 05:45 PM - edited 2024-10-18 05:53 PM
I have two MCUs and I connected them by SPI, one of them is master and another is slave.
On slave MCU, I used two SPI1 and SPI2 and I connected them serially by wire, sometimes connect and disconnect
them by S1, I want to ask is it possible to have this switch by software?
Solved! Go to Solution.
2024-10-21 01:53 AM - edited 2024-10-21 02:27 AM
you mean I can, reprogram GPIO to change SPI pins to manage what I want to do, just I have a question, is it possible I just remap MISO pin and rest pins remain as before?
Yes you can by updating the GPIOx->MODER as appropriate. The only caveat is that you'll be writing the whole 32-bit register. So you have to read the value, update the bits you want to change then write it back.
// with port as GPIOx
// bit as whichever bit it is 0 to 15
// mode as 0 for input, 1 for output (recommended), 2 to restore alt-function
unsigned long mask2 = ~(3ul << (2 * bit));
port->MODER = (port->MODER & mask2) | (((3 & (unsigned long)mode)) << (2 * bit));
If you have multiple threads or interrupts that might touch the same MODER then you will have to manage access to it yourself.
(Edit: Corrected allowed range for bit number in code snippet)
2024-10-19 09:50 AM
Yes it can be done.
But before I go on to say how, I would like you to explain why this is something you want to do. Not because I need to know, but because this seems (to me) such a strange request that either you have a particularly unusual requirement or you have misanalysed your problem in coming up with that approach. Normally (nowadays) people have slaves wired in parallel with individual SSELs for each. (In the past people would treat each SPI as a shift-register and chain them together, but what do you want to go into SPI#2 when the switch is open).
I will say that having the switch open / turned-off means that the MOSI input to SPI#2 is floating, not driven or pulled high or low. This is a "bad thing" in CMOS microcontroller circuit design because the voltage could float to somewhere between Vdd and Vss, leading to increased power wastage. Also the wire could pick up stray signals or noise from elsewhere, so who knows what data will seem to arrive at MOSI for SPI#2.
And the way I would open the switch is to reprogram the GPIO pin that had been configured for SPI1's MISO back as a regular GPIO by writing 00 or 01 into the appropriate bits in GPIOx->MODER. The way to do this is all in the Reference Manual for your stm32; I know this is a huge document which takes effort to start understanding, but that only reflects how powerful the stm32 microcontrollers are.
I don't know if this is possible in HAL (I don't use HAL because I feel it isn't adequately documented), but you might find reinitialising SPI1 with SPI_DIRECTION_2LINES_RXONLY does the trick.
2024-10-20 03:03 PM
Thank you so much,
You are right, I didn't draw my complete circuit diagram, and I just made a simple schematic that can focus on my issue better.
you mean I can, reprogram GPIO to change SPI pins to manage what I want to do, just I have a question, is it possible I just remap MISO pin and rest pins remain as before?
2024-10-21 01:53 AM - edited 2024-10-21 02:27 AM
you mean I can, reprogram GPIO to change SPI pins to manage what I want to do, just I have a question, is it possible I just remap MISO pin and rest pins remain as before?
Yes you can by updating the GPIOx->MODER as appropriate. The only caveat is that you'll be writing the whole 32-bit register. So you have to read the value, update the bits you want to change then write it back.
// with port as GPIOx
// bit as whichever bit it is 0 to 15
// mode as 0 for input, 1 for output (recommended), 2 to restore alt-function
unsigned long mask2 = ~(3ul << (2 * bit));
port->MODER = (port->MODER & mask2) | (((3 & (unsigned long)mode)) << (2 * bit));
If you have multiple threads or interrupts that might touch the same MODER then you will have to manage access to it yourself.
(Edit: Corrected allowed range for bit number in code snippet)