Tuesday, November 10, 2015

Linux Kernel



http://segmentfault.com/a/1190000002754840
http://coolshell.cn/articles/7965.html
下面输出了多少个“g”?
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>

int main(void)
{
   int i;
   for(i=0; i<2; i++){
      fork();
      printf("g");
   }

   wait(NULL);
   wait(NULL);

   return 0;
}
  • fork()系统调用是Unix下以自身进程创建子进程的系统调用,一次调用,两次返回,如果返回是0,则是子进程,如果返回值>0,则是父进程(返回值是子进程的pid),这是众为周知的。
  • 还有一个很重要的东西是,在fork()的调用处,整个父进程空间会原模原样地复制到子进程中,包括指令,变量值,程序调用栈,环境变量,缓冲区,等等。
所以,上面的那个程序为什么会输入8个“-”,这是因为printf(“-“);语句有buffer,所以,对于上述程序,printf(“-“);把“-”放到了缓存中,并没有真正的输出(参看《C语言的迷题》中的第一题),在fork的时候,缓存被复制到了子进程空间,所以,就多了两个,就成了8个,而不是6个。
另外,多说一下,我们知道,Unix下的设备有“块设备”和“字符设备”的概念,所谓块设备,就是以一块一块的数据存取的设备,字符设备是一次存取一个字符的设备。磁盘、内存都是块设备,字符设备如键盘和串口。块设备一般都有缓存,而字符设备一般都没有缓存
对于上面的问题,我们如果修改一下上面的printf的那条语句为:
1
printf("-\n");
或是
1
2
printf("-");
fflush(stdout);
就没有问题了(就是6个“-”了),因为程序遇到“\n”,或是EOF,或是缓中区满,或是文件描述符关闭,或是主动flush,或是程序退出,就会把数据刷出缓冲区。需要注意的是,标准输出是行缓冲,所以遇到“\n”的时候会刷出缓冲区,但对于磁盘这个块设备来说,“\n”并不会引起缓冲区刷出的动作,那是全缓冲,你可以使用setvbuf来设置缓冲区大小,或是用fflush刷缓存。
我估计有些朋友可能对于fork()还不是很了解,那么我们把上面的程序改成下面这样:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
int main(void)
{
   int i;
   for(i=0; i<2; i++){
      fork();
      //注意:下面的printf有“\n”
      printf("ppid=%d, pid=%d, i=%d \n", getppid(), getpid(), i);
   }
   sleep(10); //让进程停留十秒,这样我们可以用pstree查看一下进程树
   return 0;
}
于是,上面这段程序会输出下面的结果,(注:编译出的可执行的程序名为fork)
1
2
3
4
5
6
7
8
9
10
ppid=8858, pid=8518, i=0
ppid=8858, pid=8518, i=1
ppid=8518, pid=8519, i=0
ppid=8518, pid=8519, i=1
ppid=8518, pid=8520, i=1
ppid=8519, pid=8521, i=1
$ pstree -p | grep fork
|-bash(8858)-+-fork(8518)-+-fork(8519)---fork(8521)
|            |            `-fork(8520)
面对这样的图你可能还是看不懂,没事,我好事做到底,画个图给你看看:
注意:上图中的我用了几个色彩,相同颜色的是同一个进程。于是,我们的pstree的图示就可以成为下面这个样子:(下图中的颜色与上图对应)
这样,对于printf(“-“);这个语句,我们就可以很清楚的知道,哪个子进程复制了父进程标准输出缓中区里的的内容,而导致了多次输出了。(如下图所示,就是我阴影并双边框了那两个子进程)
http://www.onkarjoshi.com/blog/191/device-dev-random-vs-urandom/
/dev/random will block after the entropy pool is exhausted. It will remain blocked until additional data has been collected from the sources of entropy that are available. This can slow down random data generation.

/dev/urandom will not block. Instead it will reuse the internal pool to produce more pseudo-random bits.

/dev/urandom is best used when:

You just want a large file with random data for some kind of testing.
You are using the dd command to wipe data off a disk by replacing it with random data.
Almost everywhere else where you don’t have a really good reason to use /dev/random instead.
/dev/random is likely to be the better choice when:

Randomness is critical to the security of cryptography in your application – one-time pads, key generation.
http://www.onkarjoshi.com/blog/191/device-dev-random-vs-urandom/
There are a few things about /dev/urandom and /dev/random that are repeated again and again. Still they are false.

/dev/urandom is insecure. Always use /dev/random for cryptographic purposes.
Fact: /dev/urandom is the preferred source of cryptographic randomness on UNIX-like systems.
/dev/urandom is a pseudo random number generator, a prng, while /dev/random is a “true” random number generator.
Fact: Both /dev/urandom and /dev/random are using the exact same csprng(a cryptographically secure pseudorandom number generator). They only differ in very few ways that have nothing to do with “true” randomness.
/dev/random is unambiguously the better choice for cryptography. Even if /dev/urandom were comparably secure, there's no reason to choose the latter.
Fact: /dev/random has a very nasty problem: it blocks.
http://www.cyberciti.biz/faq/bash-shell-script-generating-random-numbers/
Each time this is referenced, a random integer between 0 and 32767 is generated. 
for i in {1..5}; do echo $RANDOM; done
Using /dev/urandom or /dev/random
od -vAn -N4 -tu4 < /dev/urandom
od -An -N2 -i /dev/random



Labels

Review (572) System Design (334) System Design - Review (198) Java (189) Coding (75) Interview-System Design (65) Interview (63) Book Notes (59) Coding - Review (59) to-do (45) Linux (43) Knowledge (39) Interview-Java (35) Knowledge - Review (32) Database (31) Design Patterns (31) Big Data (29) Product Architecture (28) MultiThread (27) Soft Skills (27) Concurrency (26) Cracking Code Interview (26) Miscs (25) Distributed (24) OOD Design (24) Google (23) Career (22) Interview - Review (21) Java - Code (21) Operating System (21) Interview Q&A (20) System Design - Practice (20) Tips (19) Algorithm (17) Company - Facebook (17) Security (17) How to Ace Interview (16) Brain Teaser (14) Linux - Shell (14) Redis (14) Testing (14) Tools (14) Code Quality (13) Search (13) Spark (13) Spring (13) Company - LinkedIn (12) How to (12) Interview-Database (12) Interview-Operating System (12) Solr (12) Architecture Principles (11) Resource (10) Amazon (9) Cache (9) Git (9) Interview - MultiThread (9) Scalability (9) Trouble Shooting (9) Web Dev (9) Architecture Model (8) Better Programmer (8) Cassandra (8) Company - Uber (8) Java67 (8) Math (8) OO Design principles (8) SOLID (8) Design (7) Interview Corner (7) JVM (7) Java Basics (7) Kafka (7) Mac (7) Machine Learning (7) NoSQL (7) C++ (6) Chrome (6) File System (6) Highscalability (6) How to Better (6) Network (6) Restful (6) CareerCup (5) Code Review (5) Hash (5) How to Interview (5) JDK Source Code (5) JavaScript (5) Leetcode (5) Must Known (5) Python (5)

Popular Posts