2011-10-08 6 views
3

ARM 마이크로에서 OLED 디스플레이에 표시하기 위해 snprintf가있는 문자열에 정수를 인쇄하려고합니다. 그러나 % d 또는 % u를 사용하면 마이크로가 잠기고 실행이 중지됩니다. % x 또는 % c를 사용하면 문제가 없지만 출력은별로 유용하지 않습니다.% d 또는 % u를 표시 할 때 snprintf가 중단된다

이 문제가 발생할 수있는 이유는 무엇입니까? 불행히도 디버깅 할 JTAG 장치에 액세스 할 수 없습니다. 나는 arm-none-eabi-gcc를 사용하여 컴파일하고 있으며 모두 메이플 미니로 실행 중입니다.

UPDATE

전달 값 < (10)는 작동하도록 보인다.

+0

'int'를 스택으로 밀어 넣고 있습니까? '% d'는'% c'보다 큽니다. 그래서'char'를 누르면'% c'와 함께 작동하지만'% d'과 충돌합니다.'snprintf'를 호출 할 때'yourvariable' 대신'(int) yourvariable'을 지정하십시오. –

+2

@ todda.speot.is : 올바르지 않습니다. 'printf'에 전달되면,'% d'와'% c'는 모두 같은 타입을 지정합니다 :'int'. –

+0

프로모션 유형! 나는 잊었다. –

답변

2

실제로 사용하고있는 RTOS에서 스택 크기 문제로 판명되었습니다. snprintf 호출의 추가 된 복잡성이 한계를 넘기고 충돌하는 것 같았습니다.

누구나 답변 해 주셔서 감사합니다!

0

%x%u이 모두 같은 유형을 지정하므로 형식 오류 일 수 없습니다. 따라서 snprintf 그 자체에서 문제가되어야합니다. 이 둘 사이의 가장 큰 차이점은 %u은 정수를 나눠야하고 나머지는 계산해야한다는 점입니다. 반면에 %x은 쉬프트와 마스크로 얻을 수 있습니다.

C 라이브러리가 사용하고있는 ARM 프로세서와 다른 다양한 종류의 ARM 프로세서 용으로 컴파일되었을 가능성이 있으며, 불법 명령어를 사용하여 몫 또는 나머지를 계산하는 중일 수 있습니다.

Cortex M3 용 라이브러리를 컴파일하고 있는지 확인하십시오. 예 :

+0

-mcpu가 이미 cortex-m3으로 설정되어 있으며 유형 문제에 동의합니다. snprintf에 몇 가지 문제가 있다고 생각했지만 ARM과 같은 공통 아키텍처에서 기본이 제대로 작동하지 않는다는 것에 놀랐습니다. 틀림없이 ** something ** wrong : P – aliask

0

범위가 프로토 타입입니까? snprintf()는 varargs 함수이고, varargs를 호출하면 함수가 기대하는 곳에서 인수를 얻으려면 몇 가지 속임수가 필요할 수 있습니다.

또한 항상은 varargs 함수를 호출 할 때 적절한 유형을 사용합니다. ('%'다음에 오는 것은 snprintf()가 어딘가에서 찾을 것으로 기대하는 타입이고, '어딘가'는 타입에 의존 할 수도 있습니다.) 당신의 경우 : "% X"는 unsigned int를 기대합니다. 함수 호출에서 매개 변수를 형변환하거나 "unsigned int sweeplow;"를 사용하여 함수를 제공하십시오. 그것을 정의 할 때. 부정적인 빈도 또는 카운트는 어쨌든 말이되지 않습니다.

+0

프로토 타입을 추가해도 변경되지 않았고 불행히도 유형을 가지고 놀지도 않았습니다. – aliask

+0

-Wall 및 -Wstrict-prototypes가있는 경우에도 컴파일이 제대로 수행됩니까? – wildplasser

+0

-Wall을 사용하지만 -Wstrict_prototypes는 사용하지 않습니다 (코드가 의존하는 라이브러리를 컴파일하는 동안 실패 함) – aliask

1

전달 값 <이 작동하는 것처럼 보입니다.

누락되거나 작동하지 않는 분할 루틴이있는 것처럼 들립니다. printf/sprintf는 대개 십진수를 10으로 나누어 인쇄합니다. 10보다 작은 숫자의 경우 나누기가 필요하지 않으며 아마 그 이유가 될 수 있습니다.

확인하려면 두 변수를 나누는 함수를 만듭니다 (상수로 나누는 것은 일반적으로 컴파일러에서 곱하기로 최적화됩니다). 예 :

int t() 
{ 
    volatile int a, b; // use volatile to prevent compiler optimizations 
    a = 123; 
    b = 10; 
    return a/b; 
}; 

또한 빌드 로그에서 링크 경고를 확인하십시오.

관련 문제