汇编实现strcpy

需要有两点注意:

  1. .type在windows的mingw上无法识别。
  2. windows下编译会找不到my_strcpy的定义(undefined reference),通过看mingw的代码发现,它会在汇编函数前加一个下划线,所以在我们的汇编代码中加上下划线即可。

维基百科中关于cdecl的阐述,中文版有一条:编译后的函数名前缀以一个下划线字符,但英文版中没有这一条。
且加上下划线后在windows下mingw虽然不再报错,但在linux下gcc又会报undefined reference。
具体原因尚不明确。

32位

.text

.globl my_strcpy
.type my_strcpy, @function #.type伪指令在windows下编译会无法失败,可以去掉

my_strcpy:

	movl 8(%esp), %edx	#source
	movl 4(%esp), %eax	#dest

	pushl %ebp			#保存旧栈底
	movl %esp, %ebp 	#保存栈顶,结束时恢复

	movb (%edx), %cl 	#从source取一个字节,放到cl
	test %cl, %cl		#判断cl是否为0

	je return			#为0就return

body:
	movb %cl, (%eax) 	#把从source取的一个字节放到dest
	movb 1(%edx), %cl	#取source的下一个字节
	inc %eax			#递增dest索引
	inc %edx			#递增source索引
	test %cl, %cl		#判断取的字节是否为0
	jne body			#不为0就继续循环

return:
	movl $0, (%eax)		#给dest的字符串结尾加上'\0'
	
	movl %ebp, %esp		#恢复栈顶
	popl %ebp			#恢复栈底
	ret					#返回

64位

.text

.globl my_strcpy
.type my_strcpy, @function

_my_strcpy:
    pushq %rbp
    movq %rsp, %rbp

    movq %rdi, %rdx #dest
    movq %rsi, %rax #src

    movb (%rax), %cl
    test %cl, %cl

    je return
body:
    movb %cl, (%rdx)
    movb 1(%rax), %cl
    inc %rax
    inc %rdx
    test %cl, %cl
    jne body

return:
    movq $0, (%rdx)
    
    movq %rbp, %rsp
    popq %rbp
    ret

使用

main.c:

#include <stdio.h>

extern void my_strcpy(char*, const char*);

int main(void)
{
	char str_1[1024];
	char str_2[]="hello world";

	my_strcpy(str_1, str_2);

	puts(str_1);
}

假设my_strcpy定义在my_strcpy.s汇编代码文件中。

对于32位,编译:gcc main.c my_strcpy.s -o main -m32,64位不带-m32就行了。

链接器可能会报可执行堆栈的警告:

/usr/bin/ld: warning: /tmp/ccJvbhJo.o: missing .note.GNU-stack section implies executable stack
/usr/bin/ld: NOTE: This behaviour is deprecated and will be removed in a future version of the linker

可以加上-z noexecstack,或者在汇编代码里面加上这一行:

.section	.note.GNU-stack,"",@progbits
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

barbyQAQ

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值