Перейти к содержанию
    

On 8/6/2023 at 4:03 PM, jcxz said:

(так как не использую у себя всякие uintXX_t):.

Почему ?

On 8/6/2023 at 3:45 PM, jcxz said:

Зачем его заставлять??? Он по дефолту их использует - см. листинг выше. ЧЯДНТ?? :unknw:

В Compiler Exploler, который приводили по ссылке выше, компиляторы версии выше 9 не используют "UMLAL".

А версия 9 и ниже - используют.

 :unknw:

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

9 часов назад, dimka76 сказал:

Почему ?

Так короче ж запись. Я тоже переопределил себе всякие uintXX_t в uXX.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

19 часов назад, AVI-crak сказал:

Очень просто, для него все операции имеют входные и выходные операнды размером с регистр. Нужно дополнительно указывать варианты событий с иным результатом. В моём случае это дополнительное (uint64_t), без него будет выполнено обычное умножение u32=u32*u32.

Что-то Вы путаете. По правилам, ваши операнды (перед умножением) будут иметь тип uint64_t, и доп. приведений не требуется.

Поэтому везде, где у Вас приведение (uint64_t) - это лишний текст, ни к чему не приводящий.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

1 час назад, Arlleex сказал:

Так короче ж запись. Я тоже переопределил себе всякие uintXX_t в uXX.

За то uintXX_t это более стандартно... Хотя, самого бесит это зоопарк при портировании, есть стандатрная uint32_t но воткнут Uint32_t, u32, U32, u32_t и пр...

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

15 минут назад, mantech сказал:

За то uintXX_t это более стандартно... Хотя, самого бесит это зоопарк при портировании, есть стандатрная uint32_t но воткнут Uint32_t, u32, U32, u32_t и пр...

Именно поэтому у меня есть свой заголовочный файл с типами, где есть typedef uint32_t u32 и т.д.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

3 минуты назад, Arlleex сказал:

Именно поэтому у меня есть свой заголовочный файл с типами,

Дак и у меня есть, куда деваться-то))) Так и приходится его тащить из проекта в проект... Хотя нет-нет да и приходится его апдейтить всякими uchar, BYTE  и пр. фигней...

Изменено пользователем mantech

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

4 часа назад, AVI-crak сказал:

К вопросу - зачем всё это нужно. https://godbolt.org/z/8jbzqEeed

А ошибки и спец. значения как обрабатываются?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Пока ещё не обрабатываются, и куча дополнительных условий без обработки. На данный момент у меня борьба с последним битом double.

В общем оригинальный православный sscanf(), так-же как ptintf() - содержит в себе полноценную таблицу множителей на все степени двойки. 40килобайт - это от жирной таблицы. У мня есть желание избавится от таблицы, и упаковаться в размер меньше 1 килобайта. Фетиш такой, под старость лет.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Расширенным поиском нашлось очень много материала на данную тему, в том числе очень старые темы.

В целом ситуация странная. С очень давних времён была написана функция с ошибкой, которая вошла во все компиляторы без исключения. Создано огромное количество программного обеспечения, и даже аппаратные решения в новых процессорах подогнаны под ошибочные результаты. А всё потому, что если сделать правильно - то отвалится чуть-ли не половина созданного ранее. Дабы сделать плавный переход на верные результаты - практически все компиляторы исключили нативную поддержку чисел выше int64_t. Для того чтобы общество само разобралось чего кому нужно, и чтоб ненужное и глюкавое отвалилось само собой.

Плавный переход затянулся на 12 лет.

Числа большой разрядности необходимы для программной эмуляции long double : мантисса 64 бита, степень 15 бит, знак 1 бит. Когда-то очень давно для интела появилась аппаратная поддержка double, так вот внутри оно обрабатывалось как long double, и не очень честно.

uint64_t mult64toH128(uint64_t val1, uint64_t val2, int32_t* ord)
{
    uint32_t c1c0 = (uint64_t) (val1 & 0xffffffff) * (val2 & 0xffffffff) >> 32;
    uint64_t a2a1 = (val1 & 0xffffffff) * (val2 >> 32) ;
    uint64_t b2b1 = (a2a1 & 0xffffffff)+ c1c0 + (val1 >> 32) * (val2 & 0xffffffff);
    uint64_t c3c2 = (a2a1 >> 32) + (b2b1 >> 32) + (val1 >> 32) * (val2 >> 32) ;
    *ord += c3c2 >> 63;
    if((c3c2 >> 63) == 0){
        c3c2 <<= 1;
        c3c2 |= (b2b1 >> 31) & 1;
    };
    return c3c2;
}

Шланг 16,0,0 делает простой и быстрый код для кортекса М4 и выше.

  push {r4, lr}
  umull r12, lr, r2, r0
  ldr r4, [sp, #8]
  umull r12, r0, r3, r0
  umaal lr, r12, r2, r1
  umaal r0, r12, r3, r1
  ldr r1, [r4]
  lsr.w r3, lr, #31
  lsl.w r2, r12, #1
  cmp.w r12, #0
  add.w r1, r1, r12, lsr #31
  itt pl
  orrpl.w r12, r2, r0, lsr #31
  orrpl.w r0, r3, r0, lsl #1
  str r1, [r4]
  mov r1, r12
  pop {r4, pc}

Команда umaal работает так: u64 = u32+u32+u32*u32, при этом два первых операнда находятся в выходных регистрах. Так вот, GCC отказывается применять эту команду, хотя прекрасно знает о её существовании. А всё потому что очень боится переполнения, и боится не без причины. Дело в том что аппаратная поддержка double выполняется на том-же куске кремния что и простое умножение. Однако если простое умножение ограничено в разрядности, то умное от интел имеет более высокую разрядность и автоматическое округление. Ситуации когда из длинного FFFFF.... получаются нули - не столь уж и редки.

Описать ситуации исключения переполнения для double и простого умножения - для GCC оказалось непосильной задачей. А потому там просто пометка - низя.

Похоже ждать у моря погоды придётся очень долго. Даже раст отказался от поддержки int128_t - напоролся на те-же грабли.  

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

1 час назад, AVI-crak сказал:

В целом ситуация странная.

 

1 час назад, AVI-crak сказал:

Плавный переход затянулся на 12 лет.

 

1 час назад, AVI-crak сказал:

Числа большой разрядности необходимы для программной эмуляции long double

Если это действительно так, то произошло просто потому, что это оочень редко кому было нужно, ИМХО...

Изменено пользователем mantech

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Когда говорят, что вдруг нашли ошибку, которая 12 лет оставалась незамеченной и тиражировалась повсюду, "меня гложут смутные сомнения", не ошибается ли сам автор "открытия"? Потому как чаще всего (как показывает практика) ложное открытие делается по причине банальной невнимательности и собственной ошибки. 

Всё-таки, CM7 имеет 32-битное АЛУ, поэтому требовать от него аппаратную 128-битную арифметику - ну эт как-то таво...

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

On 8/12/2023 at 9:37 PM, EdgeAligned said:

"меня гложут смутные сомнения"

Например ARM выполняет честную арифметику с плавающей точкой, с округлением к нулю. Всё что не влезает в итоговый результат - просто отбрасывается. x86-64 учитывает результат намного глубже, а в части операций производит округление к единице. Если вычислений слишком много - то ошибка накапливается в младших знаках, и её уже становится видно.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...