Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: ANSI С
Форум разработчиков электроники ELECTRONIX.ru > Сайт и форум > В помощь начинающему > Программирование
Буратино
a] Есть переменная "Keys" с типом long long (64bits), в алгоритме понадобилось выставить в единички все разряды. Правильно ли я делаю:
Код
typedef  unsigned  long long  INT64U;   /* Unsigned 64 bit value  */
...
Keys = ~(INT64U)0;


b] Можно ли использовать MODE_CONTR в качестве ключа в свиче? Ругается компилятор однако..
Код
#define MODE_CONTR 1;

...
void FSMGeneral (void) {

    switch (Mode) {
        case MODE_CONTR:
            if (MsgGetMessage (MSG_SEND_COMMAND) == 1) {
                switch (Get_Type_Commands (Keys)) {
...
AHTOXA
Цитата(Буратино @ Apr 29 2011, 14:48) *
b] Можно ли использовать MODE_CONTR в качестве ключа в свиче? Ругается компилятор однако..
Код
#define MODE_CONTR 1;
Он на точку с запятой ругается.
Буратино
Цитата(AHTOXA @ Apr 29 2011, 12:30) *
Он на точку с запятой ругается.


блин, точно! sm.gif Спасибо!
Сергей Борщ
QUOTE (Буратино @ Apr 29 2011, 11:48) *
a] Есть переменная "Keys" с типом long long (64bits), в алгоритме понадобилось выставить в единички все разряды. Правильно ли я делаю:
CODE
typedef  unsigned  long long  INT64U;   /* Unsigned 64 bit value  */
...
Keys = ~(INT64U)0;
Да, правильно. Еще возможен вариант Keys = (INT64U)-1; А еще можно использовать stdint.h и тогда не придется определять свои типы.
Буратино
Есть такая функция:
Код
...
    typedef  unsigned  long       INT32U;   /* Unsigned 32 bit value                 */
    INT32U Leds;
...
void set_bit (INT08U number) {
    Leds = 0;
    Leds |= (1 << number);
}
...


Если аргумент больше чем 0x0E, то получаю странные результаты. В чем может быть причина? Спасибо!
sergeeff
Код
void set_bit (INT08U number) {

    Leds = (1UL << number);
}
Палыч
Цитата(Буратино @ May 5 2011, 16:27) *
В чем может быть причина? Спасибо!

В размерности константы:
Leds |= (1L << number);
msalov
Цитата(Буратино @ May 5 2011, 15:27) *
Если аргумент больше чем 0x0E, то получаю странные результаты. В чем может быть причина? Спасибо!

Видимо у вас int имеет разрядность 16 бит. Таким образом 1, которая имеет тип инт, при сдвиге переполняется и получается 0, хотя вы ожидаете 1 в старших разрядах. Лечится очень просто - укажите что 1 у вас не инт, а лонгинт.

Код
    Leds |= (1UL << number);

Буратино
Спасибо мужики ,все зафурычило! sm.gif
Буду иметь в виду.
sergeeff
Цитата(Буратино @ May 5 2011, 16:45) *
Спасибо мужики ,все зафурычило! sm.gif
Буду иметь в виду.


Совет господину Буратино: открыть файл limits.h и посмотреть, какие типы переменных какие имеют размерности в его конкретном случае.
Или один раз написать тест со всеми основными типами типа:
Код
printf("int - %d bytes\n", sizeof(int));

Многое прояснится.
Буратино
Файлов limits.h куча, на какой именно смотреть?
Скажите, поддерживается ли стандартом тип long long? Запутался окончательноsad.gif
Вот мои типы данных:

Код
typedef  unsigned  char       BOOLEAN;  /* Logical data type  (TRUE or FALSE)    */
typedef  unsigned  char       CHAR;     /* Unsigned 8 bit character              */
typedef  unsigned  char       INT08U;   /* Unsigned 8 bit value                  */
typedef  signed    char       INT08S;   /* Signed 8 bit value                    */
typedef  unsigned  short      INT16U;   /* Unsigned 16 bit value                 */
typedef  signed    short      INT16S;   /* Signed 16 bit value                   */
typedef  unsigned  long       INT32U;   /* Unsigned 32 bit value                 */
typedef  signed    long       INT32S;   /* Signed 32 bit value                   */
typedef  unsigned  long long  INT64U;   /* Unsigned 64 bit value  (if available) */
typedef  signed    long long  INT64S;   /* Signed 64 bit value  (if available)   */
typedef  float                FP32;     /* 32 bit,  single prec.  floating-point */
typedef  double               FP64;     /* 64 bit,  double prec.  floating-point */


IAR C/C++ Compiler for AVR
5.51.0 (5.51.0.50312)
C:\Program Files\IAR Systems\Embedded Workbench 5.4\avr\bin\iccavr.exe
02.11.2010 18:30:10, 11751424 bytes


Вот такая фигня восемь раз "бибикает"

Код
    for (i=0; i<sizeof(long long);i++){
        TmrFlagBeeper = 1;
        Delay_mSeconds(250);
        TmrFlagBeeper = 0;
        Delay_mSeconds(250);
    }
Idle
Цитата(Буратино @ May 21 2011, 19:21) *
Скажите, поддерживается ли стандартом тип long long? Запутался окончательноsad.gif

под ANSI принято понимать стандарт 89 года ansi, он же стандарт 90 года iso - в нём нет такого типа, не поддерживается (если поставить -strict в gcc, получишь отлуп)
а вот в стандарте iso от 99 года long long появился, в нём поддерживается
Буратино
Не знаю, что там за стандарты, но с long long одни траблыsad.gif

есть внешняя переменная
Код
extern INT64U RFID_Card;


ее значением в конкретном месте программы является 0x0000000000B8BFD6

пытаюсь выполнить проверку:
Код
if( (INT64U)RFID_Card == 0x0000000000B8BFD6) {...
if( (INT64U)RFID_Card == 0x0000000000B8BFD6ULL) {...
if( (INT64U)RFID_Card == (INT64U)0x0000000000B8BFD6ULL) {...

но адекватно работает только:
Код
if( (INT32U)RFID_Card == 0x00B8BFD6) {...


куда копать?
ReAl
«Какой такой козырёк?»
Код
#include <stdint.h>
extern uint64_t RFID_Card;
extern uint8_t aaa;
void foo()
{
        if (RFID_Card == 0x0000000000B8BFD6ULL) ++aaa;
}

IAR C/C++ Compiler for AVR
5.51.1 (5.51.1.50326)
Код
    192          void foo()
   \                     ??foo:
    193          {
   \   00000000   2E08               MOV     R0, R24
    194                  if (RFID_Card == 0x0000000000B8BFD6ULL) ++aaa;
   \   00000002   ....               LDI     R30, LOW(RFID_Card)
   \   00000004   ....               LDI     R31, (RFID_Card) >> 8
   \   00000006   8100               LD      R16, Z
   \   00000008   8111               LDD     R17, Z+1
   \   0000000A   8122               LDD     R18, Z+2
   \   0000000C   8133               LDD     R19, Z+3
   \   0000000E   8144               LDD     R20, Z+4
   \   00000010   8155               LDD     R21, Z+5
   \   00000012   8166               LDD     R22, Z+6
   \   00000014   8177               LDD     R23, Z+7
   \   00000016   ....               LDI     R30, LOW(__Constant_b8bfd6_0)
   \   00000018   ....               LDI     R31, (__Constant_b8bfd6_0) >> 8
   \   0000001A   ........           CALL    ?LL_CMP_L12
   \   0000001E   F429               BRNE    ??foo_1
   \   00000020   9100....           LDS     R16, aaa
   \   00000024   9503               INC     R16
   \   00000026   9300....           STS     aaa, R16
    195          }
   \                     ??foo_1:
   \   0000002A   2D80               MOV     R24, R0
   \   0000002C   9508               RET
   \                                 In  segment NEAR_ID, align 1, keep-with-next
   \                     `?<Initializer for 64 Bit Constant>_0`:
   \   00000000   BFD600B80000       DD 12107734, 0
   \              0000        

   \                                 In  segment NEAR_I, align 1, keep-with-next
   \   00000000                      REQUIRE `?<Segment init: NEAR_I>`
   \                     __Constant_b8bfd6_0:
   \   00000000                      DS8 8
   \   00000008                      REQUIRE `?<Initializer for 64 Bit Constant>_0`
Буратино
Еще одна интересная особенность: если я объявляю и инициализирую автоматическую переменную
INT64U Temp_RFID_Card = 0;

а затем присваиваю ей значение RFID_Card, то что либо вменяемое получить уже не могу ни там ни там.

Скажите, может быть у меня траблы с размером стека или еще что-то в этом духе?
Как поправить или проверить это дело?

Код
extern INT64U RFID_Card;

void main (void) {


  INT64U Temp_RFID_Card=0;
  INT08U i;


  InitDevice();


  while(1) {

    if(RFIDGetCard() == 1) {                // Если функция возвращает 1, то код карты получен и он записан в глобальную переменную RFID_Card

         Temp_RFID_Card=RFID_Card;

          UARTTransmitByte (0x55);                                    // метка
          for(i=0; i<8; i++) {
              UARTTransmitByte ((INT08U) RFID_Card);
              RFID_Card >>= 8;
          }
          UARTTransmitByte (0x33);                                    // метка
          for(i=0; i<8; i++) {
              UARTTransmitByte ((INT08U) Temp_RFID_Card);
              Temp_RFID_Card >>= 8;
          }
...




если заремить некоторые строки то все чики-пики
Код
extern INT64U RFID_Card;

void main (void) {


//  INT64U Temp_RFID_Card=0;
  INT08U i;


  InitDevice();


  while(1) {

    if(RFIDGetCard() == 1) {                // Если функция возвращает 1, то код карты получен и он записан в глобальную переменную RFID_Card

//         Temp_RFID_Card=RFID_Card;

          UARTTransmitByte (0x55);                                    // метка
          for(i=0; i<8; i++) {
              UARTTransmitByte ((INT08U) RFID_Card);
              RFID_Card >>= 8;
          }
//          UARTTransmitByte (0x33);                                    // метка
//          for(i=0; i<8; i++) {
//              UARTTransmitByte ((INT08U) Temp_RFID_Card);
//              Temp_RFID_Card >>= 8;
//          }
...
aaarrr
Немного не в тему, но все же: Буратино, зачем работать с номером карты как с 64-х битным числом? Какой-либо математики, кроме сравнения и подсчета хэша не нужно, а эти операции с тем же успехом можно сделать и с восемью байтами.
Буратино
Цитата(aaarrr @ May 23 2011, 09:15) *
Немного не в тему, но все же: Буратино, зачем работать с номером карты как с 64-х битным числом? Какой-либо математики, кроме сравнения и подсчета хэша не нужно, а эти операции с тем же успехом можно сделать и с восемью байтами.


Вы имеете в виду вместо long long использовать 8ми байтовый массив? Ну как вариант можно рассмотреть, но вот сейчас чиста интересна ,что не так.
Поправил настройки в ИАРе, попробую разобраться.

Поменял параметры в иаре и все заработало.
Номер карты не long long а просто long. Всем спасибо!



Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.