CS252 Mid

Premature Free: 过早释放内存

int *p = malloc(sizeof(int));
*p = 6; //将分配到内存中的值设置为6, p指针的值是*p = 6
free(p); //释放内存后,p虽然依然指向那块地址,但内存属于操作系统管理,p成为了一个悬空指针(dangling pointer),不是free(*p),因为p是指存储的地址,*p是p存储的地址里保存的值
printf("%d\n", *p);

Double Free

int *p = malloc(sizeof(int));
*p = 6;
free(p);
//free(p)后,p是dangling pointer,为了防止滥用,通常要加上p = NULL,手动清空指针
free(p);

Wild Free

int *p = malloc(sizeof(int));
*p = 6;
free(&p); // 释放了栈上的地址(指针本身的地址),应该是free(p)
int *p = malloc(sizeof(int));
*p = 6;
p = p + 1
free(p); //释放的并不是原始malloc返回的地址

Memory Smashing (Heap Buffer Overflow)

int *g = malloc(20 * sizeof(int)); //将指针看成一个数组,length = 20
g[20] = 40; //index <= 19
free(g);

Memory Leak:

int g = new int;
// new和malloc差不多,&g是指针本身的地址,g是存储值的地址,*g是值
//malloc靠free(g)来释放内存,new靠delete g来释放内存
*g = 40;
int g = new int;
*g = 41;
delete g;
int *g = malloc(sizeof(int));
*g = 6;
g = NULL;//原来存储6的地址丢失,永远无法有效free(g)

CPU-bound process是那种几乎需要一直使用CPU的进程,如果时间片(quantum)太短,会让其运行变慢。比如:

  • CPU-bound 任务需要 100ms 才能完成,如果时间片是 100ms,一次就完成;如果时间片是 10ms,它需要被调度 10 次,每次都上下文切换;总耗时更长;进程调度效率更低 - 因此,quantum越短,context switch overhead越少

Multilevel Feedback Queue (MLFQ): 一种基于优先级的调度策略,低优先级队列中的进程容易一直被高优先级进程抢占,如果不加处理,这些低优先级进程可能永远得不到 CPU 时间,即发生饥饿(starvation)

  • 奖励交互型进程(short quantum) -> 提高优先级
  • 惩罚CPU密集型进程(长时间运行) -> 降低优先级
  • 长时间低优先级,会增加其优先级

State: New -> Ready -> Running -> Exit Or New -> Ready -> Running -> Waiting -> Ready (大多数在waiting state)(处于Ready状态的进程不会直接进入waiting)

waiting: 运行中的进程遇到阻塞事件(I/O device operations)

处于运行状态的进程数量,最多等于CPU核心数(number of cores,有时候cores也称为processors)

In the malloc implement, we have a global variable header * lastFencepost, what is the use for this variable.

global: 多个函数共享lastFencepost这个信息(allocate_object, coalesce)

检查sbrk()的新内存是否是连续: lastFencepost + sizeof(fencepost) = the_start_of_new_chunk

  • 如果是连续,合并,合并过程中间的栅栏块会变成空闲内存的一部分,更新lastFencepost为新区域的最右端。
  • 如果不是,更新lastFencepost为新区域最右端
int obj_can_be_expanded(size_t new_size, int *oldptr){
   //返回0就是可以,返回1就是不行之类的,返回类型可以用int来代替bool
   //ptr是指针,指向data开始的地方,所以是*ptr, 类型应该是整数指针 
    header *h = (header*)((char*)oldptr - ALLOCATE_HEADER_SIZE);//知道指向data的ptr,如何找h
    header *rightheader = (header*)((char*)h + get_size(h));
    size_t available = get_size(h) + get_size(rightheader) - ALLOCATE_HEDAER_SIZE;
    if(get_state(rightheader) == UNALLOCATED && available >= new_size) {
        return 0; //可以扩展
    }
    return 1;
}
int heap_free_count(size_t minSize, size_t maxSize) {
    int count = 0;
    for (i = 0; i < N_LIST; i++) {
        header *freelist = &freelistSentinels[i]
        header *cur = freelist->next;
        while (cur != freelist) {
            size_t t = get_size(curr)
            if (size_t >= minSize && size_t <= maxSize){
                count++;
            }
            cur = cur->next;
        }
    }
    return count;
}
int pipe_open(char * command) {
    int fd[2]; //定义一个长度为2的整数组,用于表示一个管道的两个端点,fd[0]是读端,fd[1]是写端
    res = pipe(fd); //创建一个无名管道成功为0
    if (res != 0) {
        perror('pipe failed');
        exit(1); //异常而退出
    }
    pid_t pid = fork(); // 0 是子进程
    if (pid == 0) {
        close(fd[0]);
        dup2(fd[1], 1);//标准输出指向写端
        char ** args = parseCmd(command);//两个星表示字符串
        execvp(args[0], args);
        // only something wrong
        perror('execvp');
        exit(1);
    } else{
        close(fd[1]);//otherwise, it will hang
        return fd[0]
    }
}

char ** parseCmd(char * command) {
    int nargs = 0;
    char ** args = malloc((strlen(command) + 1) * sizeof(char*));
    char *s = strup(command);
    char *p = s;
    while (*p != '\0'){
        while (*p == ''){
            p++;
        }
        if (*p != '\0') {
            args[nargs] = p;
            nargs++;
            while (*p != '\0' and *p != ' '){
                p++;
            }
            if (*p == '\0'){
                break
            }
            if (*p = ' '){
                *p = '\0';//命令行中的end of word是'\0';
                p++;
            }
        }
        args[nargs] = NULL;
    }
    return args;
}



Enjoy Reading This Article?

Here are some more articles you might like to read next:

  • CS252 Final
  • Backtracking, LeetCode
  • Mock Interview(2), LeetCode
  • Binary Tree, LeetCode
  • NVIDIA, LeetCode