小编nrz*_*nrz的帖子

谁知道"mov edi,edi"有什么用?

69A8AB13  int         3    
69A8AB14  int         3    
69A8AB15  mov         edi,edi 
69A8AB17  push        ebp  
69A8AB18  mov         ebp,esp 
Run Code Online (Sandbox Code Playgroud)

mov edi,edi 对我来说没有意义,它是为了什么?

x86 assembly mov

12
推荐指数
2
解决办法
5093
查看次数

如何"填充"可变长度字符串以使对齐的最后一列

我有以下格式的输入:


09:08:11        XXXXXXXXXXXXX  1.1.1.1          
09:09:03        YYYYYYYY  2.2.2.2         
09:12:37        ZZZZ   3.3.3.3
Run Code Online (Sandbox Code Playgroud)

我可以使用正则表达式轻松提取这些个人字段/(\S+)\s+(\S+)\s+(\S+)\s+/.我叫他们$time,$name$number.我的问题是我想显示这个以便$number完美对齐.因为它$name可以是任何长度,对此最好的解决方案是什么?

我希望输出看起来像这样.请注意,我必须使用点来对齐最后一个字段,因为我无法使用空格键来执行此操作,不确定原因.安美居.


09:08:11        XXXXXXXXXXXXX    1.1.1.1          
09:09:03        YYYYYYYY         2.2.2.2         
09:12:37        ZZZZ             3.3.3.3
Run Code Online (Sandbox Code Playgroud)

我想把它$name放到一个数组中.然后使用函数找到字符数最长的函数.最后,我会填写较短的名称以匹配最长的名称.有没有更好,更有效的方法来做到这一点?

perl

11
推荐指数
2
解决办法
2万
查看次数

如何将Linux 32位gcc内联汇编转换为64位代码?

我正在尝试使用gcc在Linux 中将RR0D Rasta Ring 0调试器从32位模式转换为64位模式(长模式).我熟悉x86 32位程序集(在MS-DOS环境中),但我是x86 64位程序集和Linux程序集编程的初学者.

这个项目是供生产使用的(我需要一个可用的非源调试器),但我也尝试学习如何进行32位到64位的转换.如果可能的话,我试图找到一种通用的方法来进行32位到64位的转换,可以使用正则表达式在任何32位程序上完成(这样它就可以自动化).我知道没有通用的解决方案(64位代码可能占用比32位代码更多的空间等,并且消耗更多的堆栈等),但即使在这种情况下,自动转换的代码也可以作为起点.

我们的想法是保持8位和16位操作数不变,并用64位操作数替换32位操作数.如果pushw %ax; pushw %bx; popl %ecx替换为这种方法自然会失败pushw %ax; pushw %bx; popq %rcx,但是性能良好的程序通常不会有push两个16位操作数,而是pop一个32位操作数,或者它们呢?

这些是到目前为止的转换:

编辑:修复:pusha/ pushad 可以用连续的push'es 替换,因为pusha/ pushad命令在实际推送之前推送sp/ 的值,并且在286+中以相同的方式工作,但在8088/8086 汇编语言数据库中有所不同.这种差异不是问题(对于386+代码).并且因此可以与连续的替换命令.esp sppush sppushapushadpush

替代方法与OpenSolaris的privregs.h代码类似.

编辑:修复:对所有命令使用64位内存寻址.

  1. pusha- > push %ax; push %cx; push %dx; push %bx; push %sp; push %bp; push …

linux assembly gcc x86-64 inline-assembly

11
推荐指数
0
解决办法
2770
查看次数

ASM调用约定

我一直在阅读有关在ASM中调用约定的内容,这是我到目前为止的内容:

          x86(userland)    x86(kernel)    x64(userland)    x64(kernel)

1st arg           Stack           EBX               RDI            RDI
2nd arg           Stack           ECX               RSI            RSI
3rd arg           Stack           EDX               RDX            RDX
4th arg           Stack           ESI               RCX            R10
5th arg           Stack           EDI               R8             R8
6th arg           Stack           EBP               R9             R9

result            EAX             EAX               RAX            RAX
Run Code Online (Sandbox Code Playgroud)

我的问题是:

  1. 到目前为止我学到的是正确的吗?

  2. 如何在x86(内核)和x64(两者)中传递6个以上的参数?使用堆栈?介意给我一个小例子?

  3. 我有一个内核模块,我愿意从ASM调用该模块中的函数.我应该使用什么惯例?内核还是用户空间?

c x86 assembly x86-64 linux-kernel

11
推荐指数
1
解决办法
2029
查看次数

如何检查有符号整数是否为负或位?

我是x86汇编语言的新手,我有一个保存在寄存器中的有符号整数eax,我想检查数字是负数还是正数.为此,我用bt指令检查第一位.

这是我做的:

bt eax,0
jnc isNegative
Run Code Online (Sandbox Code Playgroud)

bt第一位携带标志,我用来jnc检查进位标志是0还是1.如果是1,它应该是负数,并做负指令...但是,输出是不可预测的,有时我有一个积极的,它认为它是一个负数.难道我做错了什么?

编辑:我刚刚意识到它可能与endianess有关.它实际上是检查最后一位而不是第一位.让我试试吧bt,7

x86 assembly

10
推荐指数
2
解决办法
3万
查看次数

C到汇编调用约定32位对64位

我一直在关注优秀的编程基础,希望学习装配.虽然现在不在书中,但是我想在32位机器上调用我的汇编函数,这在本书的工作中是有效的.

我在这里做的是存储第一个参数%ebx和第二个参数%ecx.

.type power, @function
.globl power
power:
    pushq   %ebp
    movl    %esp, %ebp
    subl    $4, %esp

    movl    8(%ebp), %ebx
    movl    12(%ebp), %ecx
Run Code Online (Sandbox Code Playgroud)

我将这个(以及函数的其余部分)编译成一个目标文件,创建一个main.c,在那里我对函数进行原型化并调用它,如下所示:

int power(int b, int x);
int a = power(2, 1);
Run Code Online (Sandbox Code Playgroud)

但是,当我在64位机器上编译它时,我得到一些非常意外的结果.我修改了明显的,喜欢的事实,%esp%epb需要更换与%rsp%rpb,但与GDB挖掘显示,参数是无处栈上找到!

通过使用-SGCC选项检查发生了什么我可以看到,GCC不是在堆栈上推送变量,而是将参数存储在寄存器中.

 movl $1, %esi
 movl $2, %edi
 call power
Run Code Online (Sandbox Code Playgroud)

在32位机器上,它完成我所期望的并推送堆栈上的参数:

 movl $1, 4(%esp)
 movl $2, (%esp)
 call power
Run Code Online (Sandbox Code Playgroud)

现在发生了什么事?为什么GCC在64位寄存器和32位堆栈上传递参数?这非常令人困惑!在任何地方我都找不到任何提及.有没有人可以在这种情况下启发我?

c linux x86 assembly x86-64

10
推荐指数
1
解决办法
1万
查看次数

如何更改GDB中的eflags寄存器值?

set $eflags没有改变eflags价值.

eflags例如,旧的价值仍然存在.=>$set $eflag=0x243[这只是一个输入示例].

或者,有没有办法设置个别标志eflags

我正在寻找类似的东西:set ZF[zero flag].有没有gdb命令来做到这一点?

debugging assembly flags gdb

10
推荐指数
2
解决办法
3万
查看次数

How to compile LLVM against a custom glibc?

I'm using YouCompleteMe Vim plugin for text completion (installed through Vundle). YouCompleteMe uses Clang for text completion for C-family languages (C, C++, Objective-C, Objective-C++). However, after YouCompleteMe update (via :VundleUpdate in Vim) YouCompleteMe ceased to work.

In short, the question is: How can I compile Clang against a custom glibc version? Debian Wheezy ships with glibc 2.13, and it seems that newest Clang version requires at least glibc 2.15 (explanation in more detail below). Just in case, I'm using …

vim glibc cmake llvm clang

10
推荐指数
1
解决办法
4072
查看次数

用C和汇编编写一个简单的线程

我正在尝试编写一个简单的用户级线程库作为我的OS课程的练习.作为第一步,我试图运行一个程序并跳转到一个函数离开第一个程序.到目前为止的代码是这样的:

最初的计划:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <assert.h>

#define STACK_SIZE (sizeof(void *) * 512)


void proc2() //This is the function that should run as the thread.
{
    int i;
    for(i=0;i<30;i++)
    {
        printf("Here I am!\n");
        sleep(0.5);
    }
    exit(0);
}

void* malloc_stack() //used to malloc the stack for the new thread. 
{
    void *ptr = malloc(STACK_SIZE + 16);
    if (!ptr) return NULL;
        ptr = (void *)(((unsigned long)ptr & (-1 << 4)) + 0x10); //size align
    return ptr;
}

int main() …
Run Code Online (Sandbox Code Playgroud)

c assembly x86-64

9
推荐指数
1
解决办法
647
查看次数

从64位地址加载到rax以外的其他寄存器

在x64上,可以通过以下方式从64位绝对地址加载(即,取消引用64位立即数)

movabs addr64, %rax
Run Code Online (Sandbox Code Playgroud)

但是,当目标寄存器不是rax汇编程序给出错误消息时operand size mismatch for movabs.我错过了什么?

assembly x86-64

9
推荐指数
1
解决办法
4894
查看次数

标签 统计

assembly ×8

x86-64 ×5

x86 ×4

c ×3

linux ×2

clang ×1

cmake ×1

debugging ×1

flags ×1

gcc ×1

gdb ×1

glibc ×1

inline-assembly ×1

linux-kernel ×1

llvm ×1

mov ×1

perl ×1

vim ×1