📜 ⬆️ ⬇️

First steps with STM32 and mikroC compiler for ARM architecture - Part 1

Back in my student years I had to very closely generalize with microcontrollers, then they were 8-bit 8051 and AVR. Now, wanting to return to this lesson, turned his eyes on a very wide family of controllers STM32. Much has been written about them in the open spaces of the Network; nevertheless, I expressed a desire to write a short series of articles on working with STMs. Acquaintance with them, I would like to start, as they say, with a full 0. For experiments, I purchased a simple and cheap ($ 3) Maple Mini debug board. The STM32F103CB controller used in it has a very impressive bunch of possibilities. (especially in comparison with decisions in the price category). Details can be read online, and of course, in the datasheet. . I did not immediately like the native Arduin-like development environment (taste and color, as they say ...). Out of the abundance of diverse development environments, I focused my eyes on mikroelektronika's mikroC for ARM. Once I came across their compilers (for 8081), I really liked it. Although not without jambs, but decided to try.


The board has this form, everything is very simple and concise:


image


The basic scheme of the board is also simple, but everything that is most needed here is:


image


The programmer selected the Chinese clone ST-LINK2 ($ 3), nevertheless it works fine with the mikro


image


Link to the demo version of mikroC . Demo version limitation: maximum 4KB of binary code. Not a lot, but quite enough for familiarization. There should be no problems with installing the application, the only thing you need to do is to install the driver on ST-LINK2 before running the mikroC installer.


After starting and creating a project, the application window greets us:


image


First of all, after choosing the type of microcontroller used, it is necessary to adjust the properties of our project. The configuration of the mikroC project is invoked with the keyboard shortcut Shift-Ctrl-E (Project - Edit Project). It is in this window that all the charms associated with the complex internal organization of the clocking system of STM32 microcontrollers are configured. In general, I advise you at least briefly read the Reference manual for this family of microcontrollers. We will return to it repeatedly.


image


The block diagram of the clocking system of datashita STM32F103


This window sets the configuration of the registers RCC_CR and RCC_CFGR



MSU clock frequency choose the frequency SYSCLOCK - 72 MHz (72.000000)


image


Now we can save the settings for our MK. Everything is ready for writing 1 program. As always, we blink an LED (connected to PB1 leg):


To set the output of the GPIO port to the output in the microC there is a function


GPIO_Digital_Output(&GPIO_BASE, _GPIO_PINMASK_ALL);//     

it includes GPIOx clocking and writes values ​​to the configuration register. The data that is written to the port is entered in the register GPIOx_ODR .


 GPIO_ODR = ; // c    

The compiler allows access to a particular register bit or variable. For this, the bit number (starting from 0) is written after the register name through the point


 REGx.by; //    (y)   () 

To generate delays, use the built-in function Delay_ms () (or Delay_us () ) of the compiler. Here is our first program:


 void main() { GPIO_Digital_Output(&GPIOb_BASE, _GPIO_PINMASK_1); // PB1  GPIOb_ODR.b1 = 0; //   GPIOb_ODR  15  = 0 while(1) //   { GPIOb_ODR.b1=~GPIOb_ODR.b1; // 15  Delay_ms(500); // 500  } } 

To apply one initialization command to several ports at once, write _GPIO_PINMASKn through the "or" operator, for example:


 GPIO_Digital_Output(&GPIOb_BASE, _GPIO_PINMASK_1 | _GPIO_PINMASK_7); //PB1  PB7    GPIO_Digital_Output(&GPIOa_BASE, _GPIO_PINMASK_ALL ); //  PA    

Now let's try to bring the meander to one of the MK pins, switching the output state of the PB15 port with an interval of 5 ms. :


 void main() { GPIO_Digital_Output(&GPIOb_BASE, _GPIO_PINMASK_15); GPIOb_ODR.b15 = 0; while(1) { GPIOb_ODR.b15=~GPIOb_ODR.b15; Delay_ms(5); //  5 .( 10 ,  100 ) } } 

At the pin PB15 we have the following signal:


image


If we need to read the state of the port, then we use the GPIOx_IDR register, having previously configured the port to the input using the GPIO_Digital_Input (* port, pin_mask) function. On our board there is a button connected to the pin of port PB8. The following program lights the flashing LED on pin PB1 while the button is pressed.


 void main() { GPIO_Digital_Output(&GPIOb_BASE, _GPIO_PINMASK_1); GPIO_Digital_Input(&GPIOb_BASE, _GPIO_PINMASK_8); //   PB8   GPIOb_ODR.b1 = 0; while(1) { if (GPIOb_IDR.b8) //    8  GPIOb_IDR  1 { GPIOb_ODR.b1=~GPIOb_ODR.b1; Delay_ms(500); // 500  } else { GPIOb_ODR.b1 = 0; //  ,   } } } 

On this part 1 came to an end. In the second part I will try to acquaint you with the implementation of PWM modulation, work with timers and the function of suppressing the bounce of contacts on the button.


')

Source: https://habr.com/ru/post/318306/


All Articles