Функции Variadi c имеют специальное правило для неявного продвижения типов, известное как повышение аргументов по умолчанию .
C17 6.5.2.2/7
Многоточие в объявлении прототипа функции останавливает преобразование типа аргумента после последнего объявленного параметра. Повышение аргументов по умолчанию выполняется на конечных аргументах.
Ellipsis ...
Повышения аргументов по умолчанию обычно просто используются при использовании функций, не являющихся прототипами старого стиля. Поэтому они определены как:
C17 6.5.2.2/6
Если выражение, обозначающее вызываемую функцию, имеет тип, который не содержит прототип, выполняются целочисленные повышения для каждого аргумента и аргументы типа float
повышаются до double
. Они называются продвижениями аргументов по умолчанию .
. В вашем случае char
считается целочисленным типом, а приведенное выше означает, что оно получит целое число повышенных при передаче в функцию variadi c.
Binary это означает, что ASCII ?
= 0x3F повышается до int
. AVR использует 16-битный порядок байтов, поэтому он сохраняется в памяти как 0x3F 0x00. Проблема не l ie.
Скорее, когда вы пытаетесь использовать va_arg
для неправильного типа, вы вызываете неопределенное поведение. Это указано в документации для va_arg
:
C17 7.16.1.1/2
Если фактического следующего аргумента нет или тип не совместим с типом фактический следующий аргумент (как продвигается в соответствии с продвижением аргумента по умолчанию), поведение не определено
Таким образом, единственное возможное решение - изменить код на if(t=='c') Serial.println(va_arg(args, int));
.
Независимо от вашего вопроса, использование функций variadi c и stdio.h на 8-битном MCU - очень плохая практика. Эти функции не только опасны, они также потребляют много fla sh и оперативной памяти.
Кроме того, для встроенных систем всегда следует использовать stdint.h
вместо типов по умолчанию C.