【Linux之父17年前写的这段代码,你见过吗?】
Linux之父托瓦尔兹是一个拥有十足个性的程序员。
1991年秋,托沃兹公开了Linux源代码,不求名利。
他看过去跟像是一个独行侠,他承认过自己不善交际,48岁的他仍然热爱编程。
大部分程序员网友对他印象比较深刻的就是,他曾因为Nvidia不支持Linux直接开骂“f*ck you”。
近日,这为被誉为“活着的传奇”的程序员又开始发飙了,展现了他的暴脾气。
托瓦尔兹在一封邮件中写到:“这一些纯粹都是垃圾。Intel到底还想不想把事情搞好?有没有人能找他们说说,告诉他们都TMD疯了!拜托了,如果有Intel工程师看到,和你们的主管谈谈吧。”
0、为什么托瓦尔兹会对Intel感到暴怒?
其实,托沃兹一直以来都将大部分精力都放在了开发Linux上。
这次Intel的漏洞,让他也得花费大量时间和精力,和社区一同修复解决。
可以说,托瓦尔兹简直是为Linux系统而生。他的暴脾气也是有资本的,看完他的代码你会觉得这个人简直就是天才!
1、托瓦尔兹1991年公开的Linux源代码曝光
90年代,他并没有把将Linux打造成商业系统,有人问他:会不会觉得遗憾?
他说,“如果当初没有公开Linux源代码,那才会感到遗憾;如果当初让Linux走商业化道路,那么不会发展到今天这个地步;因此,对当初的决定感到很高兴。”
有程序员网友曝出了托瓦尔兹1991年公开的Linux源代码,这引起了W3Cschool的注意,下面直接贴代码。(由于篇幅所限,可以点击以下“了解更多”查看)。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 |
/ system_call.s contains the system-call low-level handling routines. This also contains the timer-interrupt handler, as some of the code is the same. The hd-interrupt is also here. NOTE: This code handles signal-recognition, which happens every time after a timer-interrupt and after each system call. Ordinary interrupts don't handle signal-recognition, as that would clutter them up totally unnecessarily. Stack layout in 'ret_from_system_call': 0(%esp) - %eax 4(%esp) - %ebx 8(%esp) - %ecx C(%esp) - %edx 10(%esp) - %fs 14(%esp) - %es 18(%esp) - %ds 1C(%esp) - %eip 20(%esp) - %cs 24(%esp) - %eflags 28(%esp) - %oldesp 2C(%esp) - %oldss / SIG_CHLD = 17 EAX = 0x00 EBX = 0x04 ECX = 0x08 EDX = 0x0C FS = 0x10 ES = 0x14 DS = 0x18 EIP = 0x1C CS = 0x20 EFLAGS = 0x24 OLDESP = 0x28 OLDSS = 0x2C state = 0 # these are offsets into the task-struct. counter = 4 priority = 8 signal = 12 restorer = 16 # address of info-restorer sig_fn = 20 # table of 32 signal addresses nr_system_calls = 67 .globl _system_call,_sys_fork,_timer_interrupt,_hd_interrupt,_sys_execve .align 2 bad_sys_call: movl $-1,%eax iret .align 2 reschedule: pushl $ret_from_sys_call jmp _schedule .align 2 _system_call: cmpl $nr_system_calls-1,%eax ja bad_sys_call push %ds push %es push %fs pushl %edx pushl %ecx # push %ebx,%ecx,%edx as parameters pushl %ebx # to the system call movl $0x10,%edx # set up ds,es to kernel space mov %dx,%ds mov %dx,%es movl $0x17,%edx # fs points to local data space mov %dx,%fs call _sys_call_table(,%eax,4) pushl %eax movl _current,%eax cmpl $0,state(%eax) # state jne reschedule cmpl $0,counter(%eax) # counter je reschedule ret_from_sys_call: movl _current,%eax # task[0] cannot have signals cmpl _task,%eax je 3f movl CS(%esp),%ebx # was old code segment supervisor testl $3,%ebx # mode? If so - don't check signals je 3f cmpw $0x17,OLDSS(%esp) # was stack segment = 0x17 ? jne 3f 2: movl signal(%eax),%ebx # signals (bitmap, 32 signals) bsfl %ebx,%ecx # %ecx is signal nr, return if none je 3f btrl %ecx,%ebx # clear it movl %ebx,signal(%eax) movl sig_fn(%eax,%ecx,4),%ebx # %ebx is signal handler address cmpl $1,%ebx jb default_signal # 0 is default signal handler - exit je 2b # 1 is ignore - find next signal movl $0,sig_fn(%eax,%ecx,4) # reset signal handler address incl %ecx xchgl %ebx,EIP(%esp) # put new return address on stack subl $28,OLDESP(%esp) movl OLDESP(%esp),%edx # push old return address on stack pushl %eax # but first check that it's ok. pushl %ecx pushl $28 pushl %edx call _verify_area popl %edx addl $4,%esp popl %ecx popl %eax movl restorer(%eax),%eax movl %eax,%fs:(%edx) # flag/reg restorer movl %ecx,%fs:4(%edx) # signal nr movl EAX(%esp),%eax movl %eax,%fs:8(%edx) # old eax movl ECX(%esp),%eax movl %eax,%fs:12(%edx) # old ecx movl EDX(%esp),%eax movl %eax,%fs:16(%edx) # old edx movl EFLAGS(%esp),%eax movl %eax,%fs:20(%edx) # old eflags movl %ebx,%fs:24(%edx) # old return addr 3: popl %eax popl %ebx popl %ecx popl %edx pop %fs pop %es pop %ds iret default_signal: incl %ecx cmpl $SIG_CHLD,%ecx je 2b pushl %ecx call _do_exit # remember to set bit 7 when dumping core addl $4,%esp jmp 3b .align 2 _timer_interrupt: push %ds # save ds,es and put kernel data space push %es # into them. %fs is used by _system_call push %fs pushl %edx # we save %eax,%ecx,%edx as gcc doesn't pushl %ecx # save those across function calls. %ebx pushl %ebx # is saved as we use that in ret_sys_call pushl %eax movl $0x10,%eax mov %ax,%ds mov %ax,%es movl $0x17,%eax mov %ax,%fs incl _jiffies movb $0x20,%al # EOI to interrupt controller #1 outb %al,$0x20 movl CS(%esp),%eax andl $3,%eax # %eax is CPL (0 or 3, 0=supervisor) pushl %eax call _do_timer # 'do_timer(long CPL)' does everything from addl $4,%esp # task switching to accounting ... jmp ret_from_sys_call .align 2 _sys_execve: lea EIP(%esp),%eax pushl %eax call _do_execve addl $4,%esp ret .align 2 _sys_fork: call _find_empty_process testl %eax,%eax js 1f push %gs pushl %esi pushl %edi pushl %ebp pushl %eax call _copy_process addl $20,%esp 1: ret _hd_interrupt: pushl %eax pushl %ecx pushl %edx push %ds push %es push %fs movl $0x10,%eax mov %ax,%ds mov %ax,%es movl $0x17,%eax mov %ax,%fs movb $0x20,%al outb %al,$0x20 # EOI to interrupt controller #1 jmp 1f # give port chance to breathe 1: jmp 1f 1: outb %al,$0xA0 # same to controller #2 movl _do_hd,%eax testl %eax,%eax jne 1f movl $_unexpected_hd_interrupt,%eax 1: call %eax # "interesting" way of handling intr. pop %fs pop %es pop %ds popl %edx popl %ecx popl %eax iret |
转载请注明:徐自远的乱七八糟小站 » 【Linux之父17年前写的这段代码,你见过吗?】