学习日志:计算机系统的show-bytes代码的阅读以及在ubantu上的运行

    xiaoxiao2025-05-17  47

    代码总览

    show-bytes

    /* show-bytes - prints byte representation of data */ /* $begin show-bytes */ #include <stdio.h> /* $end show-bytes */ #include <stdlib.h> #include <string.h> /* $begin show-bytes */ typedef unsigned char *byte_pointer; //typedef char *byte_pointer; //typedef int *byte_pointer; void show_bytes(byte_pointer start, size_t len) { size_t i; for (i = 0; i < len; i++) printf("%p\t0x%.2x\n", &start[i], start[i]); printf("\n"); } void show_int(int x) { show_bytes((byte_pointer) &x, sizeof(int)); } void show_pointer(void *x) { show_bytes((byte_pointer) &x, sizeof(void *)); } /* $end show-bytes */ /* $begin test-show-bytes */ void test_show_bytes(int val) { int ival = val; //float fval = (float) ival; double fval = (double) ival; int *pval = &ival; printf("Stack variable ival = %d\n", ival); printf("(int)ival:\n"); show_int(ival); printf("(float)ival:\n"); show_float(fval); printf("&ival:\n"); show_pointer(pval); } /* $end test-show-bytes */ void simple_show_a() { /* $begin simple-show-a */ int val = 0x87654321; byte_pointer valp = (byte_pointer) &val; show_bytes(valp, 1); /* A. */ show_bytes(valp, 2); /* B. */ show_bytes(valp, 3); /* C. */ /* $end simple-show-a */ } void simple_show_b() { /* $begin simple-show-b */ int val = 0x12345678; byte_pointer valp = (byte_pointer) &val; show_bytes(valp, 1); /* A. */ show_bytes(valp, 2); /* B. */ show_bytes(valp, 3); /* C. */ /* $end simple-show-b */ } void float_eg() { int x = 3490593; float f = (float) x; printf("For x = %d\n", x); show_int(x); show_float(f); x = 3510593; f = (float) x; printf("For x = %d\n", x); show_int(x); show_float(f); } void string_ueg() { /* $begin show-ustring */ const char *s = "ABCDEF"; show_bytes((byte_pointer) s, strlen(s)); /* $end show-ustring */ } void string_leg() { /* $begin show-lstring */ const char *s = "abcdef"; show_bytes((byte_pointer) s, strlen(s)); /* $end show-lstring */ } void show_twocomp() { /* $begin show-twocomp */ short x = 12345; short mx = -x; show_bytes((byte_pointer) &x, sizeof(short)); show_bytes((byte_pointer) &mx, sizeof(short)); /* $end show-twocomp */ } int main(int argc, char *argv[]) { int val = 12345; if (argc > 1) { val = strtol(argv[1], NULL, 0); printf("calling test_show_bytes\n"); test_show_bytes(val); } else { printf("calling show_twocomp\n"); show_twocomp(); printf("Calling simple_show_a\n"); simple_show_a(); printf("Calling simple_show_b\n"); simple_show_b(); printf("Calling float_eg\n"); float_eg(); printf("Calling string_ueg\n"); string_ueg(); printf("Calling string_leg\n"); string_leg(); } return 0; }

    代码说明

    #include <stdio.h>

    调用库函数stdio.h用于输入和输出函数如 printf和scanf等或者可用于一些指针的宏如NULL(空指针常量)

    #include <stdlib.h>

    调用库函数stdlib.h用于与系统调用相关的函数,如内存申请malloc和释放free等

    #include <string.h>

    调用库函数string.h用于做字符串处理的函数(即与char型有关)

    typedef unsigned char *byte_pointer;

    给无符号字符型取个名字叫byte_pointer,typedef是c语言的关键字,作用是为一种数据类型定义一个新名字

    void show_bytes(byte_pointer start, size_t len)

    数组start[i]用来表示我们想要读取以start指向的位置为起始的第i个位置处的字节。len是字节数。

    printf("%p\t0x%.2x\n", &start[i], start[i]);

    “%p”表示指针输出;“%.2x”表明整数必须用至少两个数字的十六进制输出; 在格式串里,每个以“%”开始的字符序列都表示如何格式化下一个参数,例如“%d”表示输出一个十进制整数,“%f”表示输出一个浮点数,“%c”是输出一个字符。 “\t”的作用是预留8个字符的显示宽度,用于对齐。 “\n”的作用是换行,就是光标下移一行却不会移到这一行的开头,“\r”是回车,就是回到当前行的开头却不向下移一行。 Enter键按下后会执行“\n\r”。

    void show_int(int x) { show_bytes((byte_pointer) &x, sizeof(int)); } void show_float(float x) { show_bytes((byte_pointer) &x, sizeof(float)); } void show_pointer(void *x) { show_bytes((byte_pointer) &x, sizeof(void *)); }

    过程show_int、show_float、show_pointer展示了如何使用程序show_bytes来分别输出类型为int,float和void*的c程序对象的字节表示。 sizeof(T)用来返回存储一个类型为T的对象所需要的字节数。

    void test_show_bytes(int val) { int ival = val; //float fval = (float) ival; double fval = (double) ival; int *pval = &ival; printf("Stack variable ival = %d\n", ival); printf("(int)ival:\n"); show_int(ival); printf("(float)ival:\n"); show_float(fval); printf("&ival:\n"); show_pointer(pval); }

    以上为打印输出:测试显示字节

    运行结果

    unsigned char不带参数的运行结果: unsigned char 带参数的运行结果: char不带参数的运行结果:

    char带参数的运行结果: int不带参数的运行结果: int带参数的运行结果:

    对测试结果进行分析

    当定义指针为int型时,地址会加4。 当定义指针为有符号的char型时,假如遇到最高位为1时,则会出现补符号位的形式。 这与unsigned char、char、int在内存中的存储方式有关,以后使用的时候应特别注意。

    最新回复(0)