Goto page 1, 2 Next
sword
Guest
Thu Oct 19, 2017 11:01 am
Cześć,
Może nie do końca ta grupa ale wielu z Was pisze w C i może mi podpowie :)
Korzystam z takich makr, które pracują na bitach, np.:
#define setbit(VAR,Place) ( (VAR) |= (uint8_t)((uint8_t)1<<(uint8_t)(Place)) )
w programie mam zdefiniowane np.:
#define PORT_LED GPIOA
#define LED_R 0
uint8_t main_flags1, main_flags2, main_flags3;
#define FLAGA1 0
#define FLAGA2 0
i później takie wykorzystanie np.:
setbit(PORT_LED, LED_R);
setbit(main_flags, FLAGA1);
setbit(main_flags2, FLAGA2);
Przy portach to jeszcze nie jest problemu ale przy flagach trzeba
ręcznie panować nad tym w której zmiennej leży jaka flaga. Już
kilka razy szukałem przez to błędów.
Jak zrobić, żeby odwołanie do flagi było jednoznaczne, chodziło by mi
o coś takiego (co nie działa przez ten przecinek):
#define F_LED_R PORT_LED,LED_R
setbit(F_LED_R);
Wtedy w programie nie muszę się już zastanawiać gdzie leży jaki bit.
Zawsze tak pisałem w asm, a teraz mi tego brakuje :)
Pozdrawiam,
--
sword
sword
Guest
Thu Oct 19, 2017 12:15 pm
On 2017-10-19 13:47, Adam Wysocki wrote:
Quote:
sword <nick@poczta.onet.pl> wrote:
Jak zrobić, żeby odwołanie do flagi było jednoznaczne, chodziło by mi
o coś takiego (co nie działa przez ten przecinek):
#define F_LED_R PORT_LED,LED_R
setbit(F_LED_R);
#define led_set() set_bit(PORT_LED, LED_R)
Ja tych makr mam więcej, to był tylko przykład z 'setbit'.
Chodzi o to, żeby w dowolnym makrze można było podstawić port
lub flagę nie generując przy tym osobnego makra dla każdego
przypadku, np.:
setbit(F_LED_R);
clrbit(F_LED_R);
chgbit(F_LED_R);
if (valbit(F_LED_R))
--
sword
Waldemar
Guest
Thu Oct 19, 2017 12:30 pm
Am 19.10.2017 um 14:15 schrieb sword:
Quote:
On 2017-10-19 13:47, Adam Wysocki wrote:
sword <nick@poczta.onet.pl> wrote:
Jak zrobić, żeby odwołanie do flagi było jednoznaczne, chodziło by mi
o coś takiego (co nie działa przez ten przecinek):
#define F_LED_R PORT_LED,LED_R
setbit(F_LED_R);
#define led_set() set_bit(PORT_LED, LED_R)
Ja tych makr mam więcej, to był tylko przykład z 'setbit'.
Chodzi o to, żeby w dowolnym makrze można było podstawić port
lub flagę nie generując przy tym osobnego makra dla każdego
przypadku, np.:
setbit(F_LED_R);
clrbit(F_LED_R);
chgbit(F_LED_R);
if (valbit(F_LED_R))
a czemu upierasz się przy makrach? Nie możesz dać inline function?
Waldek
Adam Wysocki
Guest
Thu Oct 19, 2017 1:47 pm
sword <nick@poczta.onet.pl> wrote:
Quote:
Jak zrobić, żeby odwołanie do flagi było jednoznaczne, chodziło by mi
o coś takiego (co nie działa przez ten przecinek):
#define F_LED_R PORT_LED,LED_R
setbit(F_LED_R);
#define led_set() set_bit(PORT_LED, LED_R)
--
[ Email: a@b a=grp b=chmurka.net ]
[ Web:
http://www.chmurka.net/ ]
Sebastian BiaĹy
Guest
Thu Oct 19, 2017 6:17 pm
On 10/19/2017 1:01 PM, sword wrote:
Quote:
Wtedy w programie nie muszę się już zastanawiać gdzie leży jaki bit.
Nie musisz jesli użyjesz C++. Nie mam stosownego przykładu pod reką w
tej chwili ale kilka lat temu mając ochote ukręcić leb idiotom od
definicji rejestrow SAM7 narzeźbilem coś takiego i "sprzedałem" kod.
Napisanie tego na nowo jest w zasadzie osiągalne.
Oczywiście od razu informacja dla wszystkich co podskoczyli na hasło C++
- ten mechanizm nie genaruje ani bajta więcej w kodzie. To
metaprogramowanie na szablonach, operatorach itd, na końcu wychodzi to
samo tylko pewne i bez głupich pomyłek i wygląda prawie identycznie.
sword
Guest
Thu Oct 19, 2017 7:14 pm
On 2017-10-19 14:30, Waldemar wrote:
Quote:
Ja tych makr mam więcej, to był tylko przykład z 'setbit'.
Chodzi o to, żeby w dowolnym makrze można było podstawić port
lub flagę nie generując przy tym osobnego makra dla każdego
przypadku, np.:
setbit(F_LED_R);
clrbit(F_LED_R);
chgbit(F_LED_R);
if (valbit(F_LED_R))
a czemu upierasz się przy makrach? Nie możesz dać inline
function?
Hmm, mogę dać inline ale wydaje mi się, że jestem w tym samym
punkcie co z makrami.
static inline void setbit (u8 port, u8 pin)
{
port |= 1<<pin;
}
No i co dalej? Chciałbym ją tak samo wywołać, np.:
setbit(F_LED)
--
sword
sword
Guest
Thu Oct 19, 2017 7:15 pm
On 2017-10-19 20:17, Sebastian Biały wrote:
Quote:
On 10/19/2017 1:01 PM, sword wrote:
Wtedy w programie nie muszę się już zastanawiać gdzie leży
jaki bit.
Nie musisz jesli użyjesz C++. Nie mam stosownego przykładu
pod reką w tej chwili ale kilka lat temu mając ochote
ukręcić leb idiotom od definicji rejestrow SAM7 narzeźbilem
coś takiego i "sprzedałem" kod. Napisanie tego na nowo jest
w zasadzie osiągalne.
Oczywiście od razu informacja dla wszystkich co podskoczyli
na hasło C++ - ten mechanizm nie genaruje ani bajta więcej w
kodzie. To metaprogramowanie na szablonach, operatorach itd,
na końcu wychodzi to samo tylko pewne i bez głupich pomyłek
i wygląda prawie identycznie.
Ja mam C na sztywno w tym projekcie i nie dam rady przeskoczyć
na C++.
--
sword
Sebastian BiaĹy
Guest
Thu Oct 19, 2017 7:19 pm
On 10/19/2017 9:15 PM, sword wrote:
Quote:
Ja mam C na sztywno w tym projekcie i nie dam rady przeskoczyć
na C++.
Z powodu jakiego? Technicznego czy białkowego?
Grzegorz Niemirowski
Guest
Thu Oct 19, 2017 7:38 pm
sword <nick@poczta.onet.pl> napisał(a):
Quote:
Hmm, mogę dać inline ale wydaje mi się, że jestem w tym samym
punkcie co z makrami.
static inline void setbit (u8 port, u8 pin)
{
port |= 1<<pin;
}
No i co dalej? Chciałbym ją tak samo wywołać, np.:
setbit(F_LED)
Musisz stworzyć coś, co oprócz bitu będzie nisło też informację o porcie,
np.
#include <stdio.h>
#define PINA1 0x01
#define PINA2 0x02
#define PINB2 0x02
#define PINB3 0x03
#define F_PINA1 (0x0000 | PINA1)
#define F_PINA2 (0x0000 | PINA2)
#define F_PINB2 (0x0100 | PINB2)
#define F_PINB3 (0x0100 | PINB3)
int porta = 0, portb = 0;
void setpin(unsigned int fpin);
int main() {
setpin(F_PINA1);
setpin(F_PINA2);
setpin(F_PINB2);
setpin(F_PINB3);
printf("%x %x\n", porta, portb);
return 0;
}
void setpin(unsigned int fpin){
int port = fpin >> 8;
int pin = 0x00ff & fpin;
switch(port) {
case 0x00:
porta |= 1 << pin;
break;
case 0x01:
portb |= 1 << pin;
break;
}
}
--
Grzegorz Niemirowski
http://www.grzegorz.net/
sword
Guest
Thu Oct 19, 2017 8:17 pm
On 2017-10-19 21:19, Sebastian Biały wrote:
Quote:
On 10/19/2017 9:15 PM, sword wrote:
Ja mam C na sztywno w tym projekcie i nie dam rady
przeskoczyć
na C++.
Z powodu jakiego? Technicznego czy białkowego?
Jest narzucone z "góry".
--
sword
Sebastian BiaĹy
Guest
Thu Oct 19, 2017 8:28 pm
On 10/19/2017 10:17 PM, sword wrote:
Quote:
Z powodu jakiego? Technicznego czy białkowego?
Jest narzucone z "góry".
Czyli białkowy. Nadzieja w tym że problemy białkowe czasami rozwiązują
się szybciej niż komercyjne kompilatory dostają wsparcie C++, ale to
rodzaj czarnego humoru.
To nie pomogę bo każde rozwiązanie w C będzie gówniane.
Jakub Rakus
Guest
Thu Oct 19, 2017 8:48 pm
W dniu 19.10.2017 o 13:01, sword pisze:
Quote:
Przy portach to jeszcze nie jest problemu ale przy flagach trzeba
ręcznie panować nad tym w której zmiennej leży jaka flaga. Już
kilka razy szukałem przez to błędów.
Problem moim zdaniem nie leży ani w wybranym w języku programowania, ani
w sposobie implementacji tylko "wyżej" - zagadnienie nazywa się semantyka.
Rozwiązanie banalne - stosuj nazwy zmiennych, funkcji, makr i definicji,
które będą JEDNOZNACZNE i SAMOKOMENTUJĄCE SIĘ. Dobrym przykładem mogą
być biblioteki dostarczane przez ST do ich procków, bo tam przyjęto
regułę, że jeśli rejestr nazywa się REG_BLA_BLA to bity w nim nazywają
się REG_BLA_BLA_ENABLE_COŚTAM, REG_BLA_BLA_DISABLE_INNE_COŚTAM itd.
--
Pozdrawiam
Jakub Rakus
J.F.
Guest
Fri Oct 20, 2017 12:04 am
Dnia Thu, 19 Oct 2017 21:38:58 +0200, Grzegorz Niemirowski napisał(a):
Quote:
sword <nick@poczta.onet.pl> napisał(a):
Hmm, mogę dać inline ale wydaje mi się, że jestem w tym samym
punkcie co z makrami.
static inline void setbit (u8 port, u8 pin)
{
port |= 1<<pin;
}
No i co dalej? Chciałbym ją tak samo wywołać, np.:
setbit(F_LED)
Musisz stworzyć coś, co oprócz bitu będzie nisło też informację o porcie,
np.
[...]
A na bezczelnego ?
#define F_LED GPIO,7
.... setbit(F_LED) ...
https://gcc.gnu.org/onlinedocs/cpp/Argument-Prescan.html
J.
Marcin
Guest
Fri Oct 20, 2017 9:43 am
Quote:
Do takiego zadzialania potrzeba "podwojnego makra":
#define _test_set_bit(port,pin) do{ (port)->PDOR |=(1<<(pin)); }while(0)
#define test_set_bit(x) _test_set_bit(x)
#define LEG_G_7 GPIOB,7
i wtedy
test_set_bit(LEG_G_7);
preprocesor rozwinie poprawnie:
do{ (((GPIO_Type *)(0x400FF040u)))->PDOR |=(1<<(7)); }while(0);
Przy pojedynczym makro (jak pierwsze) arm-none-eabi-gcc zglasza blad ze makro ma miec 2 parametry a przekazany jest tylko 1.
$ arm-none-eabi-gcc -E -mcpu=cortex-m0plus makro.c -o makro2.lst
makro.c:14:23: error: macro "test_set_bit" requires 2 arguments, but only 1 given
test_set_bit(LEG_G_7);
Marcin
Janusz
Guest
Fri Oct 20, 2017 9:53 am
W dniu 2017-10-19 o 13:01, sword pisze:
Quote:
Cześć,
Może nie do końca ta grupa ale wielu z Was pisze w C i może mi podpowie :)
Korzystam z takich makr, które pracują na bitach, np.:
Ja to robię tak wpierw definicje makr
#define SET_(p, m) (p |= (1 << (m)))
#define CLR_(p, m) (p &= ~(1 << (m)))
#define TEST_(p,m) (p & (1 << (m)))
#define TOGGLE_(p, m) (p ^= (1 << (m)))
#define SET(x) SET_(x)
#define CLR(x) CLR_(x)
#define TEST(x) TEST_(x)
#define TOGGLE(x) TOGGLE_(x)
potem właściwa konfiguracja
#define ZIELONA PORTB,1
i potem w programie
SET(ZIELONA);
--
Pozdr
Janusz
Goto page 1, 2 Next