我是C的新手,我的任务是重新创建string.h标准库(或者至少是最流行的命令)。我们已经获得了一个“测试程序”程序来自动检查我们的工作,并且还要求我们的代码使用switch-std = c99和-Wall进行编译,并且在通过valgrind运行时没有错误。
虽然我的代码工作且没有编译问题,但valgrind给了我几个错误,所有错误都是Conditional jump or move depends on uninitialised value(s)
。
我对这个错误的理解是我正在使用一个尚未初始化为值的变量。无论我怎么努力,我都找不到一个未初始化的变量。我在想这个问题,我的问题可能与指针有关,但是我对C语言的理解程度不高,无法用我的代码找到问题。
以下是我的工作。
#include <stdlib.h>
size_t my_strlen(const char* s){
size_t count = 0;
while(*s != '\0'){
count++;
s++;
}
return count;
}
char* my_strcpy(char* tgt, const char* src){
while(*src != '\0'){
*tgt = *src;
tgt++;
src++;
}
return tgt;
}
int my_strcmp(const char* s1, const char* s2){
while(*s1 != '\0'){
if(*s1 != *s2){
if(*s2 == '\0'){
return 1;
}
else if(*s1 > *s2){
return 1;
}
else{
return -1;
}
}
s1++; s2++;
}
if(*s2 != '\0'){
return -1;
}
return 0;
}
char* my_strcat(char* tgt, const char* src){
while(*tgt != '\0'){
tgt++;
}
while(*src != '\0'){
*tgt = *src;
src++;
tgt++;
}
return tgt;
}
char* my_strchr(const char *s, int c){
while(*s != '\0'){
if(*s == (char) c){
return (char*) s;
}
s++;
}
return NULL;
}
char* my_strrchr(const char *s, int c){
char* last = NULL;
while(*s != '\0'){
if(*s == (char) c){
last = (char*) s;
}
s++;
}
return last;
}
这是测试人员(不是我自己写的):
#include <stdio.h>
#include "project.h"
#include <assert.h>
#include <string.h>
#include <stdlib.h>
int SIGN(int x) {
if(x < 0) { return -1; }
if(x > 0) { return +1; }
return 0;
}
/* Gold testing: compare the results of your functions to the results
of functions known correct for the same computational problem. */
int main() {
int i, j;
int M = 200;
char* s1 = malloc((M+1) * sizeof(char));
char* s2 = malloc((M+1) * sizeof(char));
char* s3 = malloc((M+1) * sizeof(char));
printf("Starting out the CPS 393 project test program.\n");
for(i = 0; i < M; i++) {
s1[i] = 'a' + (rand() % 26);
}
s1[i] = '\0';
assert(strlen(s1) == my_strlen(s1));
printf("Passed stage one. Current score: 3\n");
fflush(stdout);
for(i = 0; i < M; i++) {
for(j = i; j < M; j++) {
my_strcpy(s2, s1 + j);
strcpy(s3, s1 + j);
assert(SIGN(strcmp(s2, s3)) == SIGN(my_strcmp(s2, s3)));
}
}
printf("Passed stage two. Current score: 8\n");
fflush(stdout);
for(i = 0; i < M; i++) {
assert(strlen(s1 + i) == my_strlen(s1 + i));
for(j = 0; j < M; j++) {
assert(SIGN(strcmp(s1 + i, s1 + j)) == SIGN(my_strcmp(s1 + i, s1 + j)));
}
}
printf("Passed stage three. Current score: 12\n");
fflush(stdout);
for(i = 0; i < M; i++) {
for(j = 'a'; j <= 'z'; j++) {
assert(strchr(s1 + i, j) == my_strchr(s1 + i, j));
assert(strrchr(s1 + i, j) == my_strrchr(s1 + i, j));
}
}
free(s2);
free(s3);
printf("Passed stage four. Current score: 16\n");
fflush(stdout);
s2 = malloc(M*M*sizeof(char));
s3 = malloc(M*M*sizeof(char));
s2[0] = '\0';
s3[0] = '\0';
for(i = 0; i < M; i++) {
strcat(s2, s1 + i);
my_strcat(s3, s1 + i);
}
assert(strcmp(s2, s3) == 0);
printf("Passed stage five. Current score: 20\n");
fflush(stdout);
free(s1);
free(s2);
free(s3);
printf("Test program for 393 project completed.\n");
return 0;
}
这是valgrind给我的东西(我已经包含了--track-origin = yes,因为我读过它有助于找到问题。虽然没有帮助我!):
==16780== Memcheck, a memory error detector
==16780== Copyright (C) 2002-2010, and GNU GPL'd, by Julian Seward et al.
==16780== Using Valgrind-3.6.0.SVN-Debian and LibVEX; rerun with -h for copyright info
==16780== Command: ./project
==16780==
Starting out the CPS 393 project test program.
Passed stage one. Current score: 3
==16780== Conditional jump or move depends on uninitialised value(s)
==16780== at 0x40256E3: strcmp (mc_replace_strmem.c:426)
==16780== by 0x8048919: main (in 393/project)
==16780== Uninitialised value was created by a heap allocation
==16780== at 0x4023F50: malloc (vg_replace_malloc.c:236)
==16780== by 0x80487E0: main (in 393/project)
==16780==
==16780== Conditional jump or move depends on uninitialised value(s)
==16780== at 0x40256D5: strcmp (mc_replace_strmem.c:426)
==16780== by 0x8048919: main (in 393/project)
==16780== Uninitialised value was created by a heap allocation
==16780== at 0x4023F50: malloc (vg_replace_malloc.c:236)
==16780== by 0x80487E0: main (in 393/project)
==16780==
==16780== Conditional jump or move depends on uninitialised value(s)
==16780== at 0x80486D5: my_strcmp (in 393/project)
==16780== by 0x8048937: main (in 393/project)
==16780== Uninitialised value was created by a heap allocation
==16780== at 0x4023F50: malloc (vg_replace_malloc.c:236)
==16780== by 0x80487E0: main (in 393/project)
==16780==
Passed stage two. Current score: 8
Passed stage three. Current score: 12
Passed stage four. Current score: 16
==16780== Conditional jump or move depends on uninitialised value(s)
==16780== at 0x8048700: my_strcat (in 393/project)
==16780== by 0x8048C53: main (in 393/project)
==16780== Uninitialised value was created by a heap allocation
==16780== at 0x4023F50: malloc (vg_replace_malloc.c:236)
==16780== by 0x8048C04: main (in 393/project)
==16780==
==16780== Conditional jump or move depends on uninitialised value(s)
==16780== at 0x40256E3: strcmp (mc_replace_strmem.c:426)
==16780== by 0x8048C76: main (in 393/project)
==16780== Uninitialised value was created by a heap allocation
==16780== at 0x4023F50: malloc (vg_replace_malloc.c:236)
==16780== by 0x8048C04: main (in 393/project)
==16780==
Passed stage five. Current score: 20
Test program for 393 project completed.
==16780==
==16780== HEAP SUMMARY:
==16780== in use at exit: 0 bytes in 0 blocks
==16780== total heap usage: 5 allocs, 5 frees, 80,603 bytes allocated
==16780==
==16780== All heap blocks were freed -- no leaks are possible
==16780==
==16780== For counts of detected and suppressed errors, rerun with: -v
==16780== ERROR SUMMARY: 203 errors from 5 contexts (suppressed: 13 from 8)