我创建了一个最小的C++程序:
int main() {
    return 1234;
}
Run Code Online (Sandbox Code Playgroud)
并使用clang ++ 5.0编译它并禁用优化(默认值-O0).生成的汇编代码是:
  pushq %rbp
  movq %rsp, %rbp
  movl $1234, %eax # imm = 0x4D2
  movl $0, -4(%rbp)
  popq %rbp
  retq
Run Code Online (Sandbox Code Playgroud)
我理解大多数行,但我不明白"movl $ 0,-4(%rbp)".似乎程序将一些局部变量初始化为0.为什么?
什么编译器内部细节导致此存储不对应源中的任何内容?
我对程序集完全陌生,在搜索之后我仍然对寄存器有一些疑问。目前我正在尝试通过执行以下操作一遍又一遍地划分值:
1.将 ax 与 bl 相除(似乎余数去 ah,商去 al)
2.move al(quotient) to ax
3. 如果 ax 小于或等于 0,则跳转到 5
4.跳到1
5.结束
问题出现在指令 2 上,因为我试图将 8 位值移动到 16 位值。有人知道如何解决问题吗?
我使用的是 emu8086,所以寄存器只有 x、h 和 l。
我正在春季启动。我有一种使用字节数组返回文件的方法。而我试图返回字节数组时出现此错误。我的代码如下-
@GetMapping(
      value = "/get-file",
      produces = MediaType.APPLICATION_OCTET_STREAM_VALUE
    )
    public @ResponseBody byte[] getFile() throws IOException {
        InputStream in = getClass()
          .getResourceAsStream("/com/baeldung/produceimage/data.txt");
        return IOUtils.toByteArray(in);
    }
Run Code Online (Sandbox Code Playgroud) 这是一组示例函数,第一个是20个args,第二个是2:
int a(int n1, int n2, int n3, int n4, int n5, int n6, int n7, int n8, int n9, int n10, int n11, int n12, int n13, int n14, int n15, int n16, int n17, int n18, int n19, int n20) {
    return n1 * n2 * n3 * n4 * n5 * n6 * n7 * n8 * n9 * n10 * n11 * n12 * n13 * n14 * n15 * n16 * n17 * n18 * …Run Code Online (Sandbox Code Playgroud) 我在拦截器中读取请求正文时遇到问题。两者getReader()都会getInputStream()造成问题。我的拦截器:
public class MyInterceptor extends HandlerInterceptorAdapter {
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception exception)
        throws Exception {
    // TODO Auto-generated method stub
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
        throws Exception {
    // TODO Auto-generated method stub
}
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
    String requestBody = httpRequest.getReader().lines().collect(Collectors.joining(System.lineSeparator()));
//or
// String requestBody = new BufferedReader(new InputStreamReader(httpRequest.getInputStream()))
//                .lines().collect(Collectors.joining("\n"));
//some logic...
    return …Run Code Online (Sandbox Code Playgroud) 我正在编写一个简单的引导程序,并且有一个getch功能。
char getch()
{
   uint16_t inchar;
   __asm__ __volatile__ ("int $0x16\n\t"
                        : "=a"(inchar)
                   : "0"(0x0));
   return (char)inchar;
}
Run Code Online (Sandbox Code Playgroud)
我尝试了第一个显而易见的解决方案,即删除inchar变量对char的强制转换,但是当我打印它时,仍然返回char而不是代码。
我的println实现:
void println(char *str)
{
    while (*str) 
    {
        // AH=0x0e, AL=char to print, BH=page, BL=fg color
        __asm__ __volatile__ ("int $0x10"
                              :
                              : "a" ((0x0e<<8) | *str++),
                                "b" (0x0000));
    }
}
Run Code Online (Sandbox Code Playgroud)
链接描述文件:
ENTRY(start);
SECTIONS
{
    . = 0x7C00;
    .text : {
        /* Place the code in hw.o before all other code */
        boot.o(.text);
        *(.text);
    }
    /* Place …Run Code Online (Sandbox Code Playgroud) 在 llvm pass 模块中编写一些内联程序集后,我收到此错误:
<inline asm>:1:2: error: unkown use of instruction mnemonic without a size suffix
        test %rsi, $1
        ^
Run Code Online (Sandbox Code Playgroud)
我的理解是这个错误意味着我正在尝试使用指令不支持的操作数大小,或者大小不明确。我仔细阅读了 Intel x86_64 软件开发手册,我相当确定我明确指定了“REX.W + F7 /0 id”或“TEST r/m64,imm32”操作。我需要更明确地说我想要 REX 版本吗?如何?
我想在链接器脚本中定义一个部分,并在运行时从源代码中获取其值。
到目前为止,我已经采用了默认gcc linker脚本文件,并添加了我的部分,如下所示:
...
.my_section : { BYTE(0xAA); }
...
Run Code Online (Sandbox Code Playgroud)
编译后,我可以看到以下部分:
> gcc -T ls.ld main.c -o main
> objdump -h main
...
...
 27 .my_section   00000001  0000000000a01040  0000000000a01040  00001040  2**0
                  CONTENTS, ALLOC, LOAD, DATA
 28 .comment      00000034  0000000000000000  0000000000000000  00001041  2**0
                  CONTENTS, READONLY
Run Code Online (Sandbox Code Playgroud)
现在,我想将该值打印到stdout(并且我期望获得0xAA):
#include <stdio.h>
static volatile unsigned char SECTION __attribute__((section(".my_section")));
int main(){
    printf("hello %d\n", SECTION);
    return 0;
}
Run Code Online (Sandbox Code Playgroud)
我获得的值始终为 0。我做错了什么?
我正在开发自己的引导加载程序 + 内核。我创建了一个项目放在github上:https : //github.com/rprata/ubootlua(分支tmp-libc-implementation)
我尝试使用 QEMU 运行我的 boot.bin:
qemu-system-i386 -fda boot.bin -nographic -serial stdio -monitor none
但是会发生崩溃:
> qemu-system-i386 -fda ./deploy/boot.bin -nographic -serial stdio -monitor none
> WARNING: Image format was not specified for './deploy/boot.bin' and probing guessed raw.
>         Automatically detecting the format is dangerous for raw images, write operations on block 0 will be restricted.
>         Specify the 'raw' format explicitly to remove the restrictions.
> qemu: fatal: Trying to execute code outside RAM or …Run Code Online (Sandbox Code Playgroud) 有什么办法可以将计时器设置为 60 秒 xor ah,ah
 Enter_Again:
    xor ah, ah ; I should put 60 seconds here
    int 16h    ; The user should press S before 60 seconds
    mov bl,al
            cmp al,"S"
Run Code Online (Sandbox Code Playgroud)