Я хочу получить немного обугливания на MPLAB XC8, но не могу?

Моя функция, чтобы получить бит:

extern volatile unsigned char Temp       @ 0x036;
extern volatile __bit W       @ (((unsigned) &Temp)*8) + 4;

void get_bit(volatile unsigned char *reg, unsigned num) {
    W = (*reg & (1 << num));
}

Основная функция:

int main() {
    volatile unsigned char ch = 0b00001000;
    get_bit(&ch, 4);
}

Когда я компилирую этот код блоков, я получаю сообщение об ошибке (ошибка: синтаксис выражения).

Что я могу сделать, чтобы решить эту проблему?


person Bahtiyar Bayram    schedule 06.07.2017    source источник
comment
Куда идет значение W (и где оно определено?)?   -  person Eugene Sh.    schedule 06.07.2017
comment
Какая строка 195?   -  person Weather Vane    schedule 06.07.2017
comment
Вы ожидаете 1 в качестве вывода? Или 8? Вы всегда получите 0. Потому что 1‹‹4 равно 0b010000. И это при условии, что существует такая вещь, как двоичная константа. 0b010000 и 0b01000 равны 0.   -  person Yunnosch    schedule 06.07.2017
comment
Мой код очень большой, поэтому строка 195 не важна.   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
@BahtiyarBayram Номер строки, в которой находится ошибка, определенно важен.   -  person Eugene Sh.    schedule 06.07.2017
comment
Я ожидаю получить бит char (1 или 0) с функцией get_bit().   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
@ЕвгенийШ. Число указывает на get_bit(&ch, 4); линия.   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
Ужасный стиль программирования. Сложно оптимизировать компилятором, полно побочных эффектов. Почему бы не получить бит возврата (*reg & (1‹‹num));. А в основном W = get_nit(.....); И ваш код будет оптимизирован как раз до W=0;   -  person 0___________    schedule 06.07.2017
comment
Я составил программу из вашего неполного сообщения, используя volatile int W;, и получил чистую компиляцию и выполнение от MSVC.   -  person Weather Vane    schedule 06.07.2017
comment
@Yunnosch Я изменил этот код (W = (*reg & (1 ‹‹ num));) на этот (W = (*reg & (1 ‹‹ (num-1)));). Но ошибка все еще существует.   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
Я почти уверен, что ошибка не там, где вы думаете...   -  person Eugene Sh.    schedule 06.07.2017
comment
@ЕвгенийШ. посмотрите эту картинку: [ссылка] (ibb.co/cUAGkF) . Этот код простой, но в моем сложном коде ошибка в строке, о которой я сказал.   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
Невозможно сгенерировать код для этого выражения, поскольку оно означает нечто иное, чем синтаксис выражения. Вероятно, это как-то связано с определением W. Он определяется с использованием специального синтаксиса XC8. Для тестирования попробуйте определить его как в стандартном C, что-то вроде int W;.   -  person Eugene Sh.    schedule 06.07.2017
comment
@ЕвгенийШ. Ты прав. Я сделал то, что вы говорите, и все было хорошо, и у меня не было никаких проблем. Но я хочу сохранить 1 бит в переменной __bit. Как я могу это сделать?   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
Я бы начал с удаления extern вещей. Эти мне кажутся подозрительными.   -  person Eugene Sh.    schedule 06.07.2017
comment
@ЕвгенийШ. Я удалил эту вещь, но ошибка все еще существует.   -  person Bahtiyar Bayram    schedule 06.07.2017
comment
Я решил это. Я сделал очень глупую ошибку. Угадай, что? Я где-то забыл поставить точку с запятой. Спасибо за все.   -  person Bahtiyar Bayram    schedule 06.07.2017


Ответы (1)


Попробуйте этот код:

#include <stdio.h>

unsigned char get_bit(unsigned char reg, unsigned num) 
{
    return (reg & (1 << num));
}

unsigned char get_bit2(unsigned char reg, unsigned num) 
{
    return (reg & (1 << num))?1:0;
}

int main() 
{
    volatile unsigned char ch = 0b00001000;

    ch |= (1<<4);   // To set bit 4
    printf("%d\n",get_bit(ch, 4)); // If you try on a PC
    printf("%d\n",get_bit2(ch, 4)); // If you try on a PC

    ch &= (~(1<<4));   // To reset bit 4
    printf("%d\n",get_bit(ch, 4)); // If you try on a PC
    printf("%d\n",get_bit2(ch, 4)); // If you try on a PC


    return 0;
}
person Sir Jo Black    schedule 06.07.2017
comment
возврат (reg & (1 ‹‹ num))?1:0???? return !!(reg & (1 ‹‹ num)) — легко оптимизировать. - person 0___________; 06.07.2017
comment
Я хочу использовать указатели, потому что в будущем я бы рискнул состоянием бита. - person Bahtiyar Bayram; 06.07.2017
comment
@БахтиярБайрам. Чтобы установить бит, вы можете просто использовать ch |= (1<<4), как в моем коде, но используя символ без знака * вместо символа без знака: volatile unsigned char *ch; *ch |= (1<<bitpos);. Я предлагаю вам создать функции set, reset и get (или макросы, я думаю, что лучше) для управления битовыми операциями. - person Sir Jo Black; 07.07.2017
comment
@БахтиярБайрам. (cond)?iftrue:iffalse — тернарный оператор. Этот оператор возвращает значение iftrue, если условие истинно, иначе возвращает значение iffalse. Функция get_bit2() возвращает 1, если бит, указанный num, установлен в 1, 0, если бит, указанный num, установлен в 0. Функция get_bit() возвращает (1<<num), если бит установлен в 1, иначе она возвращает 0. - person Sir Jo Black; 07.07.2017
comment
@БахтиярБайрам. Очевидно, что когда вы используете volatile unsigned char *, прежде чем работать как *ch |= (1<<num), вы должны установить значение ch, чтобы указать подходящий регистр/память: ch = regmemval. - person Sir Jo Black; 07.07.2017