Акей.ARV писал(а):в том то и дело, что физически адресное пространство строго линейное и адресуется исключительно машинными словами. форматирование данных по типам, структурам и массивам - это уже более высокий уровень абстракции (мы уходим от машинных слов к "челвекоудобным" понятиям), поэтому ваше утверждение не совсем корректно.
вот по поводу стандарта - соглашусь полностью, но это и есть мой вариант ответа: сказано с 0, значит с 0 - и без вопросов!
Вопросы по С/С++ (СИ)
- Сообщения: 353
- Зарегистрирован: Вс янв 19, 2014 22:41:55
Одновременным нажатием LIGHT и POWER, РП Sangean ATS-909X (ver 1.29) превращается в ATS-909XR! 
- Реклама
нашол документальное подтверждение

- Вложения
-
- Выделение_008.png
- (118.53 КБ) 652 скачивания
Tell Me The Truth
FreshMan, обратите внимание на следующее.
Напримере для x86 платформы. Указатель это адрес байта в памяти. И если взять указатель на uint32_t, то инкремент такого указателя на единицу приведёт к увеличению байтового адреса на sizeof(uint32_t). Что тоже показано (косвенно) на приведённой вами картинке.
Это будет справедливо для любой платформы с учётом её особенностей.
Напримере для x86 платформы. Указатель это адрес байта в памяти. И если взять указатель на uint32_t, то инкремент такого указателя на единицу приведёт к увеличению байтового адреса на sizeof(uint32_t). Что тоже показано (косвенно) на приведённой вами картинке.
Это будет справедливо для любой платформы с учётом её особенностей.
Когда уже ничего не помогает - прочтите, наконец, инструкцию.
Лучший оптимизатор находится у вас между ушей. (Майкл Абраш, программист Quake и QuakeII)
Избыток информации ведёт к оскудению души - Леонтьев А. (сказано в 1965 г.)
Лучший оптимизатор находится у вас между ушей. (Майкл Абраш, программист Quake и QuakeII)
Избыток информации ведёт к оскудению души - Леонтьев А. (сказано в 1965 г.)
Здравствуйте коты:)
Пытаюсь запустить пример webclient на uip, под CooCox, там есть такая конструкция:
void *uip_appdata;
...
++((char *)uip_appdata); // я так понимаю, это инкремент указателя
На строчку с инкрементом ругается: error: lvalue required as increment operand
Пытаюсь запустить пример webclient на uip, под CooCox, там есть такая конструкция:
void *uip_appdata;
...
++((char *)uip_appdata); // я так понимаю, это инкремент указателя
На строчку с инкрементом ругается: error: lvalue required as increment operand
Осилит дорогу идущий
--------------------------
Пишу на Си за еду
--------------------------
Пишу на Си за еду
чем плох вариант uip_appdata++; ???
если рассматривать человека снизу, покажется, что мозг у него глубоко в жопе
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
- Реклама
А даст ли компилятор это сделать ?ARV писал(а):uip_appdata++; ???
На сколько я понимаю, указатель на void - указатель на "неизвестно чего". Соответственно, для инкремента компилятору нужно знать размер этого "неизвестно чего".
Возможно, я ошибаюсь, и по стандарту void* - указатель на байт ?
указатель void* трактуется именно как указатель на байтАlex писал(а):по стандарту void* - указатель на байт ?
если рассматривать человека снизу, покажется, что мозг у него глубоко в жопе
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
Вопрос по применению макроса.
IAR, Си, STM8S
Задача следующая:
- у меня есть переменная системного времени sys_time, которая тикает по прерыванию таймера.
Я хочу безопасно пользоваться этой величиной.
Вначале я сделал такую функцию:
И пользовался вызовом:
Переменная sys_time объявлена статической в файле таймеров и защищена от изменения извне. Возможно только чтение.
Но ИАР не хочет инлайнить функцию в простое обращение к памяти. Вызывает call даже при максимальной оптимизации. Перенос переменной в глобальную область видимости не помогает.
Применение #pragma inline = forsed тоже не помогает.
Я попробовал сделать дефайн
и вызываю его в программе:
Так в ассемблере макрос превращается в обращение к памяти, но остаётся пустая переменная dt, на которую жалуется компилятор.
Как правильно поступить в такой ситуации?
IAR, Си, STM8S
Задача следующая:
- у меня есть переменная системного времени sys_time, которая тикает по прерыванию таймера.
Я хочу безопасно пользоваться этой величиной.
Вначале я сделал такую функцию:
Код: Выделить всё
inline uint16_t time (void)
{
return sys_time;
}Код: Выделить всё
LED_start_time = time ();Но ИАР не хочет инлайнить функцию в простое обращение к памяти. Вызывает call даже при максимальной оптимизации. Перенос переменной в глобальную область видимости не помогает.
Применение #pragma inline = forsed тоже не помогает.
Я попробовал сделать дефайн
Код: Выделить всё
#define SYS_TIME(t) (t = sys_time)
Код: Выделить всё
uint16_t dt;
LED_start_time = SYS_TIME(dt);
Как правильно поступить в такой ситуации?
Прочитать жалобу компилятора...
"Я не даю готовых решений, я заставляю думать!"(С)
ну так по-вашему выходит, что макрос надо использовать так: SYS_TIME(LED_start_time);GARMIN писал(а): Я попробовал сделать дефайни вызываю его в программе:Код: Выделить всё
#define SYS_TIME(t) (t = sys_time)Так в ассемблере макрос превращается в обращение к памяти, но остаётся пустая переменная dt, на которую жалуется компилятор.Код: Выделить всё
uint16_t dt; LED_start_time = SYS_TIME(dt);
Как правильно поступить в такой ситуации?
только у меня вопрос: нафига все это?! инлайнить функцию из другого модуля компилятор по идее не будет все равно...
если рассматривать человека снизу, покажется, что мозг у него глубоко в жопе
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
dt становится неиспользуемой переменной. Присваивание идёт настоящей переменной. dt нужна для того, чтобы исключить случайную запись в sys_time.HHIMERA писал(а):Прочитать жалобу компилятора...
Что, никто не сталкивался с защитой переменных?
Может, ЛИ что подскажет.
Вообще, я хочу такую функцию, которая бы раскрывалась в код:
Код: Выделить всё
221 disableInterrupts();
\ 00002E 9B SIM
222 LED_start_time = SYS_TIME(dt);
\ 00002F CE .... LDW X, L:sys_time
\ 000032 CF .... LDW L:LED_start_time, X
223 enableInterrupts();
\ 000035 9A RIMКод: Выделить всё
if ((SYS_TIME(dt) - LED_start_time) > TIME_DISPLAY_CHANNEL)
{}- Сообщения: 535
- Зарегистрирован: Вт авг 28, 2012 22:21:33
Что за самоцель такая? Хочешь защитить её? Ну так уже защитил, сделав статической и предоставив метод для доступа. Зачем обязательно делать её inline?
Накладные расходы на вызов функции и возврат значения. Хочу избежать CALLF.
Наверное, много хочу
Наверное, много хочу
- Сообщения: 535
- Зарегистрирован: Вт авг 28, 2012 22:21:33
Я уже тут на форуме сто раз говорил. Ненужно заниматься предварительной оптимизацией! Тем более, если экономятся какие-то крохи! Сам раньше много раз попадался в эту ловушку, теперь, слава богу, отучился.
Понимаешь, если ты провел исследования, и выяснил, что узкое место - это действительно вызов функции, то может быть два варианта:
1. Выбранная тобой архитектура всего приложения - дерьмо.
2. Твоя задача действительно требует большой вычислительной мощности. При этом тебе или нужно оставить красивости вроде инкапсуляции в покое и писать всё на ассемблере оптимизируя каждый такт, или нужно взять более мощное железо.
Если никакие исследования не проводились, и это - оптимизация ради оптимизации - прошу тебя, ЗАБУДЬ!. Не херь архитектуру ради нескольких сэкономленных тактов, которые тебе никогда не пригодятся!
Понимаешь, если ты провел исследования, и выяснил, что узкое место - это действительно вызов функции, то может быть два варианта:
1. Выбранная тобой архитектура всего приложения - дерьмо.
2. Твоя задача действительно требует большой вычислительной мощности. При этом тебе или нужно оставить красивости вроде инкапсуляции в покое и писать всё на ассемблере оптимизируя каждый такт, или нужно взять более мощное железо.
Если никакие исследования не проводились, и это - оптимизация ради оптимизации - прошу тебя, ЗАБУДЬ!. Не херь архитектуру ради нескольких сэкономленных тактов, которые тебе никогда не пригодятся!
После гугления и экспериментов всё получилось.
В файле "timer.h" объявил переменную sys_time как внешнюю. Также именно в нём объявил и определил инлайн функцию с модификатором static.
Вот так:
Тогда в мэйне #include "timers.h"
и вызовы функции преобразовываются в простое чтение переменной:
Сохранена безопасность переменной, быстрота обращения и удобство написания программы.
В файле "timer.h" объявил переменную sys_time как внешнюю. Также именно в нём объявил и определил инлайн функцию с модификатором static.
Вот так:
Код: Выделить всё
extern volatile uint16_t sys_time;
inline uint16_t time (void);
static inline uint16_t time (void)
{
return sys_time;
}
и вызовы функции преобразовываются в простое чтение переменной:
Код: Выделить всё
213 LED_start_time = time ();
\ 00003D CE .... LDW X, L:sys_time
\ 000040 CF .... LDW L:LED_start_time, X- Сообщения: 535
- Зарегистрирован: Вт авг 28, 2012 22:21:33
да что тут можно сказать... человек хотел выстрелить себе в ногу и успешно этого добился...
безопасность-то соблюдена, а атомарность доступа - нет. геморрой еще впереди...
безопасность-то соблюдена, а атомарность доступа - нет. геморрой еще впереди...
если рассматривать человека снизу, покажется, что мозг у него глубоко в жопе
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
при взгляде на многих сверху ничего не меняется...
Мой уютный бложик... заходите!
- Сообщения: 535
- Зарегистрирован: Вт авг 28, 2012 22:21:33
Вот! Именно это я и хотел сказать, только слова забыл.человек хотел выстрелить себе в ногу и успешно этого добился...
По даташиту на STM8 команда "LDW X longmem" занимает три байта и выполняется за два такта процессора. Атомарность соблюдена. Это не атмел.


