我了解到,c 语言是基于汇编语言的
当开发出了第一个版本的 c 语言, 接着在第一个版本的 c 上 ,用 c 开发第二个版本的 c, 以此类推
我的理解是,这里面应该会有一些老旧的代码在 c 里(即架构、性能落后的代码)
1 、我想问问,这些年来, 汇编和 c 语言之间的桥梁有保持更新吗? 或者还是很多年前的那一套呢?
2 、 能否基于汇编开发一个比 c 更好的语言? 工作量大吗?有什么参考资料来自学吗?
谢谢
1
jmc891205 2020-12-05 17:48:01 +08:00 via iPhone 3
C++表示楼主想法很赞
|
2
cmostuor 2020-12-05 18:04:32 +08:00
C 语言的基础是 B 语言, B 语言的基础则是 Fortran 编译器+BCPL 风格而发展成的. 资料来自维基百科
|
3
creedowl 2020-12-05 18:04:52 +08:00 via Android
现在语言前端后端早就分开了,建议看看 llvm
|
4
SuperMild 2020-12-05 18:10:48 +08:00
基于啥并不重要。没有什么语言比 C 更好或更差,因为你不能说剪刀比螺丝刀更好。
|
5
ho121 2020-12-05 18:13:10 +08:00 via Android
rust ?
|
6
msg7086 2020-12-05 18:41:58 +08:00
汇编是汇编,编译语言是编译语言,不要混为一谈。
而且语言是语言,编译器是编译器,也不要混为一谈。 只要你想,拿 PHP 开发一个 C 编译器都是可以的,毕竟代码生成并没有需要用到汇编的地方。 (打个可能不恰当的比方,开发 Photoshop 的人不一定要会画画。) 用 C 的话,方便维护,然后还可以自举。 |
7
cmostuor 2020-12-05 19:03:52 +08:00 1
|
8
Cbdy 2020-12-05 19:09:10 +08:00 via Android
写个前端本来就很简单了
|
9
FutherAll 2020-12-05 19:16:00 +08:00 via iPhone 1
汇编和编程语言没有关系吧,想要的话完全可以自己写编译器实现「高级语言--汇编--机器码」的过程
|
10
natforum 2020-12-05 19:26:22 +08:00
rust 表示这个想法很好
|
12
CEBBCAT 2020-12-05 19:51:45 +08:00 via Android 1
@CEBBCAT 续:在用 Go,确实有编译到汇编这一步呀 https://colobu.com/2018/12/29/get-assembly-output-for-go-programs/
你是在说 Java 吗? |
14
OysterQAQ 2020-12-05 20:05:15 +08:00 1
汇编又叫助记符 已经很接近 cpu 指令了 现在编译器也有很多种啊 也都很智能
|
16
Ayahuasec 2020-12-05 20:41:32 +08:00 1
我记得 go 好像哪一个版本之前要用 c 来编译,过了那个版本之后就可以自己编译自己的新版本了,或许可以类比一下?
毕竟只是把语言本来的语法翻译成及其可识别的字节码,功能上看和其他程序的把输入数据转换成输出数据并没有太大区别,最开始没有工具的时候被迫用汇编,汇编创造出了工具,那之后再用工具创造新的工具就行了 |
17
find456789 OP @creedowl 大哥你好, 用 llvm 开发新语言,是不是要掌握 c\c++ 我看网上的资料 似乎是这样的
|
19
irytu 2020-12-05 21:08:22 +08:00 via iPhone 1
c 语言是基于汇编 这个说法不对,C 语言是为了更友好开发者,在编码上是更高一层的抽象,也就是你不用关心具体指令架构方面的事情,那是编译器的工作;再有汇编是跟架构指令集强相关的,而 C 不是。基本概念不能出偏差
|
20
cmostuor 2020-12-05 21:24:19 +08:00
这是龙芯 CPU AUL 模块 的指令集一小部分
cpu_gs232/blob/master/global.h /*Fix point operation*/ `define OP_CLO 8'H00 `define OP_CLZ 8'H01 `define OP_EXT 8'H02 `define OP_INS 8'H03 `define OP_WSBH 8'H04 `define OP_ROTR 8'H06 //include ROTRV `define OP_SEB 8'H08 `define OP_SEH 8'H09 `define OP_MOVN 8'H0a `define OP_MOVZ 8'H0b `define OP_MFHI 8'H0c `define OP_MFLO 8'H0d `define OP_MTHI 8'H0e `define OP_MTLO 8'H0f `define OP_MUL 8'H10 `define OP_SLL 8'H11 //include NOP,SSNOP,EHB,SLLV `define OP_SRL 8'H12 //SRLV `define OP_SRA 8'H13 `define OP_MULT 8'H14 `define OP_MULTU 8'H15 `define OP_DIV 8'H16 `define OP_DIVU 8'H17 `define OP_ADD 8'H18 //ADDI `define OP_ADDU 8'H19 //ADDIU, LUI, RDPGPR, WRPGPR `define OP_SUB 8'H1a `define OP_SUBU 8'H1b `define OP_AND 8'H1c //ANDI `define OP_OR 8'H1d //ORI `define OP_XOR 8'H1e //XORI `define OP_NOR 8'H1f `define OP_TEQ 8'H20 //TEQI `define OP_TNE 8'H21 //TNEI `define OP_TLT 8'H22 //TLTI `define OP_TLTU 8'H23 //TLTIU `define OP_TGE 8'H24 //TGEI` `define OP_TGEU 8'H25 //TEEI `define OP_SLT 8'H26 //SLTI `define OP_SLTU 8'H27 //SLTIU `define OP_MADD 8'H28 `define OP_MADDU 8'H29 `define OP_MSUB 8'H2a `define OP_MSUBU 8'H2b `define OP_J 8'H2c `define OP_JR 8'H2d //JR.HB `define OP_JAL 8'H2e `define OP_JALR 8'H2f //JALR.HB `define OP_BEQ 8'H30 `define OP_BNE 8'H31 `define OP_BLEZ 8'H32 `define OP_BGTZ 8'H33 `define OP_BLTZ 8'H34 `define OP_BGEZ 8'H35 `define OP_BLTZAL 8'H36 `define OP_BGEZAL 8'H37 `define OP_BEQL 8'H38 `define OP_BNEL 8'H39 `define OP_BLEZL 8'H3a `define OP_BGTZL 8'H3b `define OP_BLTZL 8'H3c `define OP_BGEZL 8'H3d `define OP_BLTZALL 8'H3e `define OP_BGEZALL 8'H3f cpu_gs232/blob/master/godson_alu_module.v reg [31:0]bresult; always @(sub_op or bsum_0 or bsum_1 or bsum_2 or bsum_3 or a or b or blt or eq_4 or op or braddu_temp or pick_0 or pick_1 or pick_2 or pick_3) begin case(op) // synopsys full_case parallel_case /*ADDU.QB*/ `OP_ADDQ : bresult = {bsum_3[7:0],bsum_2[7:0],bsum_1[7:0],bsum_0[7:0]}; /*ADDU_S.QB*/ `OP_ADDQ_S : bresult = {bsum_3[8] ? 8'hff : bsum_3[7:0], bsum_2[8] ? 8'hff : bsum_2[7:0], bsum_1[8] ? 8'hff : bsum_1[7:0], bsum_0[8] ? 8'hff : bsum_0[7:0]}; `OP_SUBQ : /*SUBU.QB*/ bresult = {bsum_3[7:0],bsum_2[7:0],bsum_1[7:0],bsum_0[7:0]}; `OP_SUBQ_S : /*SUBU_S.QB*/ bresult = {bsum_3[8] ? 8'h00 : bsum_3[7:0], bsum_2[8] ? 8'h00 : bsum_2[7:0], bsum_1[8] ? 8'h00 : bsum_1[7:0], bsum_0[8] ? 8'h00 : bsum_0[7:0]}; `OP_RADDU : //bresult = {22'b0, braddu_temp}; nomatch bresult = {21'b0, braddu_temp}; `OP_CMP_EQ : /*CMPGU.EQ.QB , CMPU.EQ.QB*/ bresult = {28'h0, eq_4[3], eq_4[2],eq_4[1],eq_4[0]}; `OP_CMP_LT : /*CMPGU.LT.QB , CMPU.LT.QB*/ bresult = {28'h0, blt[3], blt[2], blt[1], blt[0]}; //8'hde : `OP_CMP_LE : /*CMPGU.LE.QB , CMPU.LE.QB*/ bresult = {28'h0, (blt[3]|eq_4[3]), (blt[2]|eq_4[2]), (blt[1]|eq_4[1]), (blt[0]|eq_4[0])}; `OP_PICK : bresult = {pick_3, pick_2, pick_1, pick_0}; `OP_PRECEQU_PH_QBL : /*PRECEQU_PH_QBL*/ bresult = {{1'b0, a[31:24], 7'b0}, {1'b0, a[23:16], 7'b0}}; `OP_PRECEQU_PH_QBR : /*PRECEQU_PH_QBR*/ bresult = {{1'b0, a[15:8], 7'b0}, {1'b0, a[7:0], 7'b0}}; `OP_PRECEQU_PH_QBLA : /*PRECEQU_PH_QBLA*/ bresult = {{1'b0, a[31:24], 7'b0}, {1'b0, a[15:8], 7'b0}}; `OP_PRECEQU_PH_QBRA : /*PRECEQU_PH_QBRA*/ bresult = {{1'b0, a[23:16], 7'b0}, {1'b0, a[7:0], 7'b0}}; `OP_PRECEU_PH_QBL : /*PRECEU_PH_QBL*/ bresult = {{8'b0, a[31:24]}, {8'b0, a[23:16]}}; `OP_PRECEU_PH_QBR : /*PRECEU_PH_QBR*/ bresult = {{8'b0, a[15:8]}, {8'b0, a[7:0]}}; `OP_PRECEU_PH_QBLA : /*PRECEU_PH_QBLA*/ bresult = {{8'b0, a[31:24]}, {8'b0, a[15:8]}}; `OP_PRECEU_PH_QBRA : /*PRECEU_PH_QBRA*/ bresult = {{8'b0, a[23:16]}, {8'b0, a[7:0]}}; // `OP_REPL : /*REPL(V).QB*/ default : bresult = {a[7:0], a[7:0], a[7:0], a[7:0]}; endcase end //end always |
21
creedowl 2020-12-05 21:38:12 +08:00 via Android
@find456789 简单来说 llvm 是将中间语言编译成机器码用的,c c 艹这些都可以编译到 llvm 用的中间语言,所以想开发一个新语言写个编译器将它编译成中间语言就可以了,具体可以学学编译原理
|
22
icegaze 2020-12-05 22:12:21 +08:00 via Android 1
我感觉,
高级语言是面对人的, 低级语言是面对机器的, 中间还差着一个操作系统呢… 汇编可以看作机器码的简易代替写法, 而 C 语言可以看作一种人能理解的伪语言。 不能说 C 语言并不是基于汇编语言的吧… 甚至如果充分理解 cpu 构架和操作系统里的各种驱动的话,也可以直接用 HEX 编辑器来写出一个机器码程序了吧…^_^ |
23
find456789 OP |
24
creedowl 2020-12-05 23:24:46 +08:00
@find456789 #23 理论上是可以的
|
25
CEBBCAT 2020-12-05 23:40:49 +08:00 2
我读了 @creedowl 的回复,然后 Google 了一些关键词,花了半个小时,看了大概四五十个页面后做这个回复:
假如楼主想借由 llvm 开发一门新的语言,那么你的目标是 IR,也就是中间语言,那么结合其他语言自举的经验, 你可以使用任何一门你喜欢的语言实现一个 llvm 前端,用来把你的新语言—我们不妨叫它 X 语言—翻译到 IR,你甚至可以手写出新语言的 IR,我是这样理解的 附上一些可能有帮助的链接,你可以在里面拣选感兴趣的词,去 Google: https://draveness.me/dsl/ https://blog.csdn.net/yayaayaya123/article/details/83993041 https://segmentfault.com/a/1190000002669213 https://zh.wikipedia.org/wiki/%E4%B8%AD%E9%96%93%E8%AA%9E%E8%A8%80 https://en.wikipedia.org/wiki/Three-address_code https://blog.csdn.net/BaiHuaXiu123/article/details/89377250 --- 看完这些网页后,我想我也可以“指点”一下你的正文了: 今天的 gcc 编译器可以做到不留存“老旧的代码(即架构、性能落后的代码)”,因为 gcc 这个二进制是从它的源码来的,不是一个套娃的关系 |
26
find456789 OP |
27
whywhywhy 2020-12-06 10:37:18 +08:00
c
c++ c++++( c#) |