Error pointer of type void used in arithmetic

Over the past few weeks, some readers have encountered an error code with a void pointer, which is used for arithmetic errors. This problem occurs due to several factors. Now we will deal with them.     Requested Visited 28000 times I have experience writing and reading registers from crammap like this: // READreturn...

Approved: ASR Pro

  • 1. Download ASR Pro and install it on your computer
  • 2. Launch the program and click «Scan»
  • 3. Click «Repair» to fix any issues that are found
  • Speed up your computer’s performance now with this simple download.

    Over the past few weeks, some readers have encountered an error code with a void pointer, which is used for arithmetic errors. This problem occurs due to several factors. Now we will deal with them.

    Requested

    Visited 28000 times

    I have experience writing and reading registers from crammap like this:

      // READreturn * ((volatile uint32_t *) (roadmap + offset));// WRITE* ((volatile uint32_t *) (location + offset)) = value; 
      Warning: hint like "void *" used in math [-Wpointer-arith] 

    How do I change the code that suppresses warnings? I am using C ++ and Linux.

    pointer of type void used in arithmetic error

    requested November 5, 2014 at 11:04 am

    1321

    Not The Answer You Are Looking For? Scroll Through Other Questions Tagged With C ++ Pointers, Null Pointer, Pointer Arithmetic, Or Ask Your Own Question.

    Approved: ASR Pro

    ASR Pro is the world’s most popular and effective PC repair tool. It is trusted by millions of people to keep their systems running fast, smooth, and error-free. With its simple user interface and powerful scanning engine, ASR Pro quickly finds and fixes a broad range of Windows problems — from system instability and security issues to memory management and performance bottlenecks.

  • 1. Download ASR Pro and install it on your computer
  • 2. Launch the program and click «Scan»
  • 3. Click «Repair» to fix any issues that are found
  • Since void * is a valid pointer to an unknown type, you cannot perform pointer arithmetic because the compiler does not explicitly know the size of the object that the reference points to.

    The best way to do this is to help you convert map to a type, which was then one byte wide, and do some arithmetic. For many of them you can use uint8_t :

      // READreturn * ((volatile uint32_t *) (((uint8_t *) map) + cancel));// WRITE* ((volatile uint32_t *) (((uint8_t *) map) + decrease)) = value; 

    654

    Answered Nov 5, 2014 11:34 am

    56.6k

    pointer of type void used in arithmetic error

    The void type is an incomplete type. Its size is unknown. So show that the math with the clues to the vacuum doesn’t really make sense. You must cast a pointer that is returned to type void to a pointer of a different type. An example of a pointer can be written char.Also note that clients are not allowed to assign an object declared using the volatile qualifier.

    answered Nov 14, 14 at 11:14

    231,000

    If the way to useI arithmetic for null recommendations is really what you need, since computation is made possible by GCC (see Arithmetic for null pointers and function pointers), you can use -Wno-pointer-arith <. use / code> to suppress the warning.

    answered Jan 21 '15 at 11:20

    164

    Speed up your computer's performance now with this simple download.

    Related Posts:

    • Correct And Correct Address And Envelope Printing In Outlook 2010Correct And Correct Address And Envelope Printing In Outlook…
    • How To Fix C.defaultview.getcompputedstylea Null Is Null SimpleHow To Fix C.defaultview.getcompputedstylea Null Is Null…
    • Steps To Resolve Already Used Jboss Jvm_bind Error AddressesSteps To Resolve Already Used Jboss Jvm_bind Error Addresses
    • Steps To Correct The Absolute Calculation ErrorSteps To Correct The Absolute Calculation Error
    • Steps To Correct A Printing Error MessageSteps To Correct A Printing Error Message
    • Steps To Correct An Error In The Preun ScriptletSteps To Correct An Error In The Preun Scriptlet



    Все операции с void * кроме приведения типа уже UB. Сделай хотя бы (*(int32_t *)(buffer))++

    • Показать ответ
    • Ссылка

    Ответ на:

    комментарий
    от sambist 06.02.15 07:59:38 MSK

    См. параграф стандарта 6.5.6 Additive operators

    Стандарт определяет семантику только для случаев, когда указатель указывает на массив элементов типа T.

    Поскольку указатель типа void * не может указывать на массив (т.к. элемент с типом void невозможен), можно сделать вывод, что семантика не определена.

    Deleted

    (06.02.15 08:39:42 MSK)

    • Показать ответ
    • Ссылка

    Как я помню, указатель на void должен вмещать в себя самый длинный из указателей целевой платформы. Т.е. для 32-битной void* будет шириной в 32 бита, для 64-битной — 64.

    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 08:39:42 MSK

    Поскольку указатель типа void * не может указывать на массив (т.к. элемент с типом void невозможен), можно сделать вывод, что семантика не определена.

    не совсем так. Void* это костыль для полиморфизма в сишке. Ну например для того, что-бы реализовать malloc(3). Функция malloc(3) как раз и возвращает void*, и это вполне реальный и валидный указатель.

    Я понимаю, что это плохо, но иначе никак. Подразумевается, что размер одного «элемента» void* равен 1 char’у, хотя конечно этот «элемент» фиктивный.

    Похожая история с указателем на элемент массива, сразу за последним, он допустим, только его нельзя разыменовывать.

    int a[10];
    int* ptr = &(a[10]);// так можно
    *ptr;// а так уже нельзя
    ptr = &(a[11]);// так тоже нельзя, UB

    emulek

    (06.02.15 09:42:39 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от dnf83 06.02.15 09:47:01 MSK

    Ответ на:

    комментарий
    от emulek 06.02.15 09:50:14 MSK

    По стандарту положено ptrdiff_t для хранения разницы двух указателей. А операция вычитания определена только для операторов указывающих на один и тот же массив.

    • Показать ответ
    • Ссылка

    Ответ на:

    комментарий
    от kim-roader 06.02.15 10:10:57 MSK

    По стандарту положено ptrdiff_t для хранения разницы двух указателей.

    любые другие операции с указателями, кроме вычитания, это UB.

    А операция вычитания определена только для операторов указывающих на один и тот же массив.

    в принципе да.

    Тут вопрос к ТСу, на кой ляд ему это вычитание понадобилось-то? Пусть скастует свой void* в то, что это на самом деле, и вычитает.

    например

    uint8_t* buffer = getBuffer();
    ptrdiff_t offset = 17;// тут можно size_t
    buffer += offset;
    

    на кой ляд делать буфер хрен знает чего?

    emulek

    (06.02.15 10:20:28 MSK)

    • Показать ответ
    • Ссылка

    Ответ на:

    комментарий
    от emulek 06.02.15 10:20:28 MSK

    Тред не читай&сразу отвечай.
    С UB разобрались.
    Остался вопрос про ядро.

    Deleted

    (06.02.15 10:33:15 MSK)

    • Показать ответы
    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 10:33:15 MSK

    Тред не читай&сразу отвечай.

    если ты про

    Мне не писать, мне обоснование чтобы мочить.

    то основание у тебя уже есть, без арифметики, достаточно void *buffer = getBuffer(), потому что нет смысл выделять буфер, который невозможно использовать для хранения информации.

    Остался вопрос про ядро.

    в ядре какой-то другой стандарт?

    emulek

    (06.02.15 10:42:03 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 10:33:15 MSK

    Тебя не пустят в ядро с UB. Даже с подозрением на UB.

    • Ссылка

    компиляторы это пропускают

    gcc у меня вот так ругается

    warning: pointer of type 'void *' used in arithmetic

    обрабатывают адекватно

    Как понять «адекватно» в случае UB? Вот у меня перемещает указатель на offset байт.

    Второй вопрос — пропускают ли подобный код в ядро?

    Руки бы оторвать за такое. Больше потенциальных багов в ядре!

    А главное, нахрена? Если ты сдвигаешь указатель куда-то, значит, ты знаешь, на сколько байт ты хочешь его сдвинуть. Кастани в char* и двигай себе.

    grondek

    (06.02.15 10:47:46 MSK)

    • Показать ответ
    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 10:33:15 MSK

    Это не UB. Это запрещено в современном С (illegal), но некоторые компиляторы еще разрешают, с sizeof(void) == 1

    anonymous

    (06.02.15 10:51:14 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от grondek 06.02.15 10:47:46 MSK

    значит, ты знаешь, на сколько байт ты хочешь его сдвинуть. Кастани в char* и двигай себе.

    лучше в uint8_t*, вообще-то char не обязан быть байтом из 8и битов.

    Это не UB.

    это не UB, UB неизбежно будет ниже по коду.

    emulek

    (06.02.15 10:55:53 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 11:12:20 MSK

    Ответ на:

    комментарий
    от anonymous 06.02.15 13:02:31 MSK

    это расширение gcc

    Ага. Тогда повторю уже прозвучавший тут вопрос — а зачем так делать?

    код такой в ядре есть

    Ну надо же. Оказывается и от анонимуса польза есть.

    Deleted

    (06.02.15 14:29:44 MSK)

    • Показать ответ
    • Ссылка

    #define MAKEPTR(type,base,offs) ((type)((uintptr_t)(base)+(uintptr_t)(offs)))

    anonymous

    (06.02.15 17:12:44 MSK)

    • Ссылка

    На практике всегда было как с char*.

    anonymous

    (06.02.15 17:26:06 MSK)

    • Ссылка

    sizeof void в C равен sizeof char. в C++ не определён как sizeof неполного типа

    jtootf ★★★★★

    (06.02.15 23:23:00 MSK)

    • Показать ответ
    • Ссылка

    Ответ на:

    комментарий
    от jtootf 06.02.15 23:23:00 MSK

    sizeof void в C равен sizeof char

    В C он не определён. Равен sizeof char — это тоже расширение гцц.

    Deleted

    (07.02.15 02:54:09 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от anonymous 06.02.15 13:02:31 MSK

    Огорчу я тебя невероятно. Арифметика с void * это расширение gcc, и код такой в ядре есть, см http://lxr.free-electrons.com/source/lib/bsearch.c

    я всегда не понимал разработчиков, которые ради функции в десять строк обмазываются callback указателями. Особенно учитывая, что в большинстве случаев этот callback является обёрткой к какой-нить strcmp(3) или вообще к вычитанию двух целых чисел.

    emulek

    (07.02.15 12:01:59 MSK)

    • Ссылка

    Ответ на:

    комментарий
    от Deleted 06.02.15 14:29:44 MSK

    Ага. Тогда повторю уже прозвучавший тут вопрос

    в данном случае это полиморфизм: использования массива из хрен знает чего. Ну и тут в функцию передаётся указатель на другую функцию, которая это хрен знает что сравнивает. Если совсем упарываться, то для полноты нужна ещё одна callback, что-бы переходить к следующему эл-ту коллекции. Но вот тут сэкономили немножко, передав размер хрен знает чего.

    emulek

    (07.02.15 12:13:09 MSK)

    • Ссылка

    Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.

    Contents

    Overview

    These C compile/build errors and warnings are talked about largely in relation to embedded systems (i.e. microcontrollers).

    “pointer of type void used in arithmetic”

    Usually occurs when you are doing memory arithmetic, and can actually be a warning you ignore!

    1
    2
    3
    4
    5
    6
    
    void* AppendNewArrayElement(void* arrayStart, uint8 currNumElements, uint8 sizeOfArrayElement) {
        // Create a new option at end of option array
        arrayStart = realloc(arrayStart , (currNumElements+1)*sizeOfArrayElement);
        // Set to 0
        memset(arrayStart + currNumElements*sizeOfArrayElement, '', sizeOfArrayElement);
    }
    

    “elf section ‘.bss’ will not fit in region ‘ram’

    C build error 'elf section '.bss' will not fit in region 'ram'

    C build error ‘elf section ‘.bss’ will not fit in region ‘ram’

    The .bss section contains all 0-initialized global and static variables. This error normally occurs when you have overly large static variables, or you haven’t allocated the stack/heap sizes correctly.

    “Suggested parenthesis around assignment used as a truth value”

    A warning message from the C compiler.

    A warning message from the C compiler.

    This is usually because you’ve forgotten to add the second = in the if statement.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    
    // Only one equal sign, if statement will produce unexpected results!
    // value2 will be assigned to value1 and then
    // checked to see if non-zero
    if(value1 = value2) {
        // blah blah
    }
    
    // Correct way of comparing two values, with two equal signs
    if(value1 == value2) {
        // blah blah
    }
    

    “Subscripted value is neither array nor pointer”

    The C build error 'subscripted value is neither array nor pointer'.

    The C build error ‘subscripted value is neither array nor pointer’.

    Normally occurs when you try and index something like an array which isn’t. For example…

    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    #include 
    
    double value;
    
    // This will produce the error, as sin is a function, not an array
    value = sin[180];
    
    // The proper way of using sin
    value = sin(180);
    

    “#pragma once in main file”

    The C compiler warning '#pragma once in main file' which occurs when the directive '#pragma once' is incorrectly placed in a .c file.

    The C compiler warning ‘#pragma once in main file’ which occurs when the directive ‘#pragma once’ is incorrectly placed in a .c file.

    This occurs when you incorrectly write “#pragma once” in a .c file (even though the error would suggest it, it doesn’t have to be main.c). “#pragma once” is a header guard which prevents an .h file from being included twice in a project and causing multiple declaration/definition errors. Hence “#pragma once” should be only place in .h files. It is an alternative to the “#ifndef” header guard style (see this page for more info).

    “variable or field declared void”

    The C build error 'Variable or field declared void'.

    The C build error ‘Variable or field declared void’.

    This can occur when you declare/define a function in C++ and the compiler doesn’t recognise one of the data types used for an input variable. It will precede a <variable> was not declared in scope error.

    1
    2
    3
    
    // A function declaration with an unrecognised type used in the input.
    // The will cause both a 'variable or field declared void' and 'inputVar was not declared in scope' error
    void function1(unrecognisedType_t inputVar);
    

    “macro names must be identifiers”

    If you get the error macro names must be identifiers it is usually because you have been using both #if() and #ifdef directives, and accidentally used the combination #ifdef(). This is not allowed! When using #ifdef, do not enclose the proceeding identifier with brackets.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    // BAD!
    #ifdef(__linux)
        ...
    #endif
    
    // GOOD!
    #ifdef __linux__
        ...
    #endif
    

    “Not In Formal Parameter List”

    The 'not in formal parameter list' build error is most likely to occur when you have forgotten to add the semi-colon at the end of a function declaration.

    The ‘not in formal parameter list’ build error is most likely to occur when you have forgotten to add the semi-colon at the end of a function declaration.

    Applies To: Keil C51 Compiler

    The “not in formal parameter list” build error is most likely to occur when you have forgotten to add the semi-colon at the end of a function declaration. Without the semi-colon, the compiler continues to read onto the following lines, and usually produces this error. Check the first first function declaration preceding this error for a missing semi-colon.

    1
    2
    3
    4
    
    // The following function declaration is missing a semi-colon at the end
    void function1()
    // The "not in formal parameter list" build error will occur on this following line
    void function2();
    

    double free or corruption

    Error Type: Run Time

    This error normally codes with another keyword at the end, e.g.

    1
    
    double free or corruption (!prev)
    

    It normally occurs when you accidentally free() the same piece of memory twice. I have also got this error due to a incremental-build bug in the Xilinx SDK (xsdk) for it’s Zynq FGPAs/microcontroller chips.

    Понравилась статья? Поделить с друзьями:
  • Error po7 canon mp250
  • Error pnkbstrb was unpacked but could not be found on the file system
  • Error pngquant failed to build make sure that libpng dev is installed windows
  • Error plugin innodb registration as a storage engine failed
  • Error plugin bridge dll is not supported