注册 登录
编程论坛 汇编论坛

32汇编下为什么不用include user32.inc 声明API函数就可以使用了啊

爱末流 发布于 2012-07-27 23:11, 1863 次点击
.386
.model flat,stdcall
include Irvine32.inc
includelib user32.lib
includelib kernel32.lib
includelib irvine32.lib
.data
hello byte "this is a message!",0
caption byte "message",0
.code
main proc
mov edx,offset hello
mov ebx,offset caption
call MsgBox
main endp
end main

有些地方不解,为什么
includelib user32.lib
includelib kernel32.lib
这两句没有 用include  user32.inc 和 include kernel32.inc 啊。不用在声明API函数? 难道masn32编译时候隐含声明了吗?
就好像VC里面调用API函数也要加 windows.h头文件啊
17 回复
#2
zklhp2012-07-27 23:28
你得先明白这俩都是干啥的才能知道为什么

inc是头文件 主要放的是API的声明和相关的结构体 常量等 对于API调用来说呢 如果不包含inc文件invoke伪指令会失效 因为这时候编译器不知道函数的声明情况

lib是库文件 简单来说用于在链接时候让程序正确的调用API 如果没有它可能会出现什么【无法解析】等的问题

看了这个 你再看你的问题 不知道明白了没有
#3
爱末流2012-07-28 16:27
回复 2楼 zklhp
includelib user32.lib
includelib kernel32.lib

但是我程序没有写入API函数的声明啊。我看了 kernel32.inc 里面的文件全是API函数的调用声明 而我加了includelib user32.lib 却没有写入对应的include user32.inc文件也可以编译。
include kernel32.inc
include kernel32.inc
我看见别人的程序框架都有这两句用来声明API函数的。



就如同在VC里面 我要用API函数 就必须要加入 windows.h头文件来声明API函数,lib就不需要写了,VC会默认编译进入了= =
#4
zklhp2012-07-28 18:31
从你这个程序来讲

call MsgBox

你这个不是API 自然 不写什么kernel32.inc kernel32.lib 也是可以编译通过的 这个貌似是在那个irvine32的库里提供的罢 那样不属于系统的API 自然也不需要系统的头文件和库
#5
zklhp2012-07-28 18:36
以下是引用zklhp在2012-7-27 23:28:10的发言:

你得先明白这俩都是干啥的才能知道为什么

inc是头文件 主要放的是API的声明和相关的结构体 常量等 对于API调用来说呢 如果不包含inc文件invoke伪指令会失效 因为这时候编译器不知道函数的声明情况

lib是库文件 简单来说用于在链接时候让程序正确的调用API 如果没有它可能会出现什么【无法解析】等的问题

看了这个 你再看你的问题 不知道明白了没有

注意看我这条回复你会发现

如果不包含inc文件invoke伪指令会失效

也就是说 inc文件只在使用invoke调用API时才起作用 其他调用方式 比如call 是不起作用的 至于为啥你要是好奇我再跟你说罢

则 就算是你调用了一个系统的API 比如 MessageBox 这个是系统的API啊 但是你是用的push参数call MessageBox 调用的 不写inc也无所谓

#6
爱末流2012-07-30 17:07
回复 4楼 zklhp
kernel32.inc kernel32.lib  不加不能通过连接。他说了一大堆函数未引用的问题。
#7
爱末流2012-07-30 17:12
回复 5楼 zklhp
Irvine32 我用该书作者的这些提供的库函数,编译连接后 竟然大小为9KB= =
而不用他的函数库
我直接用windows的。
include windows.inc
include user32.inc
includelib user32.lib
include kernel32.inc
includelib kernel32.lib

我用windows的API函数。编译连接也就2KB左右的大小而已。

#8
爱末流2012-07-30 17:16
回复 5楼 zklhp
还有一个奇怪的问题。Irvine32.inc 文件里面包含了其他的inc头文件,这个包含的头文件有很多函数的声明 好象是API函数的。但是竟然没有提供 lib连接库的文件在目录下,找了好久
#9
zklhp2012-07-30 17:26
以下是引用爱末流在2012-7-30 17:12:18的发言:

Irvine32 我用该书作者的这些提供的库函数,编译连接后 竟然大小为9KB= =
而不用他的函数库
我直接用windows的。
include windows.inc
include user32.inc
includelib user32.lib
include kernel32.inc
includelib kernel32.lib

我用windows的API函数。编译连接也就2KB左右的大小而已。
对啊 这就是动态链接和静态链接的区别了 简单来讲 动态链接不会显著增大exe文件的大小 调用API大都是这样实现的 而静态链接会让exe变大
#10
zklhp2012-07-30 17:26
以下是引用爱末流在2012-7-30 17:16:17的发言:

还有一个奇怪的问题。Irvine32.inc 文件里面包含了其他的inc头文件,这个包含的头文件有很多函数的声明 好象是API函数的。但是竟然没有提供 lib连接库的文件在目录下,找了好久

关于这个库的问题呢 我就不知道了
#11
爱末流2012-07-30 23:18
回复 10楼 zklhp
额,难道作者的lib是个静态链接库? 函数全写在里面了吗?
#12
爱末流2012-08-01 19:54
回复 2楼 zklhp

我今天看到了Intel汇编程序设计 的第8章了 ,,我明白了。   首先我说 invoke 和 call 很像   invoke为更高级的调用伪指令 为call的增加版
invoke 可以用来调用子程序,但是有一点要注意就是 先声明函数的原型 就是用proto伪指令进行对函数创建一个原型(说明参数类型 参数个数)
而这个函数的声明一般在inc里面进行声明
而函数的定义 在 asm源文件进行定义,还有另外一种情况,就是不用声明函数也可以用 invoke 进行调用。那就是在它调用前 进行函数的定义。要在他前面哦

invoke 的优点显而易见 invoke 调用子程序的时候 后面跟着参数的列表,这样汇编器就为你隐含push参数进入栈,而不像call 你要为子程序传递参数时候要自己push参数进入栈中,然后子程序在用EBP进行取得参数,(用堆栈传递参数的情况下)

INVOKE 调用子程序,参数,参数,参数 隐含压入的参数.
编译后     push 参数1
           push 参数2
           push 参数n
           call 调用子程序  
在子程序就可以很好的通过名字进行引用参数了,(高级语言中的形式参数)
还有INVOKE对外部定义的函数引用也很好,直接用PROTO进行函数的声明就可以了,再者定义    而传统的call 调用外部 你就需要进行用EXTERN 进行说明了。
不过call也可以模拟 INVOKE 的调用过程 很简单。

INVOKE一般配合PROTO PROC 使用,而CALL 就配合EXTERN使用,(引用外部函数,多模块设计的时候)

INVOKE 一般用于API函数的调用,因为API函数都是用PROTO声明函数的,而且都在inc文件里面。


#13
zklhp2012-08-01 19:58
学的很快嘛 祝你早日成为大牛~
#14
zklhp2012-08-01 20:00
以下是引用爱末流在2012-8-1 19:54:51的发言:


我今天看到了Intel汇编程序设计 的第8章了 ,,我明白了。   首先我说 invoke 和 call 很像   invoke为更高级的调用伪指令 为call的增加版
invoke 可以用来调用子程序,但是有一点要注意就是 先声明函数的原型 就是用proto伪指令进行对函数创建一个原型(说明参数类型 参数个数)
而这个函数的声明一般在inc里面进行声明
而函数的定义 在 asm源文件进行定义,还有另外一种情况,就是不用声明函数也可以用 invoke 进行调用。那就是在它调用前 进行函数的定义。要在他前面哦

invoke 的优点显而易见 invoke 调用子程序的时候 后面跟着参数的列表,这样汇编器就为你隐含push参数进入栈,而不像call 你要为子程序传递参数时候要自己push参数进入栈中,然后子程序在用EBP进行取得参数,(用堆栈传递参数的情况下)

INVOKE 调用子程序,参数,参数,参数 隐含压入的参数.
编译后     push 参数1
           push 参数2
           push 参数n
           call 调用子程序  
在子程序就可以很好的通过名字进行引用参数了,(高级语言中的形式参数)
还有INVOKE对外部定义的函数引用也很好,直接用PROTO进行函数的声明就可以了,再者定义    而传统的call 调用外部 你就需要进行用EXTERN 进行说明了。
不过call也可以模拟 INVOKE 的调用过程 很简单。

INVOKE一般配合PROTO PROC 使用,而CALL 就配合EXTERN使用,(引用外部函数,多模块设计的时候)

INVOKE 一般用于API函数的调用,因为API函数都是用PROTO声明函数的,而且都在inc文件里面。

而你说的这些 让很多人诟病win32汇编是披着高级语言的汇编 其实 这是win32编程的特点决定的 是windows系统的特性决定的
#15
爱末流2012-08-01 20:32
回复 13楼 zklhp
这几天学了好多知识,呵呵。打算看完那本,我买了好多汇编的书,16位的买了6,7本了,32的汇编就3本。
还有书上的习题要慢慢做了,好多习题
#16
zklhp2012-08-01 21:28
祝成功 话说 我一本汇编的书都没有 呵呵
#17
bingghost2012-08-07 12:15
没有用过该大神的库   只是读过该大神的所著的 <<Intel程序设计第5版>>
#18
cnldrk2012-08-08 06:28
路过看看!!!!!!!
1