Modern x64 Assembly 5: MOV and LEA

แชร์
ฝัง
  • เผยแพร่เมื่อ 16 พ.ย. 2024

ความคิดเห็น • 78

  • @JimTheScientist
    @JimTheScientist 2 ปีที่แล้ว +14

    I like how casually descriptive you are about everything in your videos. It’s really nice that you’re explaining exactly what things do without using formal overly complicated terms that would only make sense to someone who already knows how to use asm.
    It’s not often that people make programming videos that are both correct and easy to understand.

  • @EnduranceT
    @EnduranceT 7 ปีที่แล้ว +57

    Wow Chris, thank you for keeping up these ASM tutorials. I'm working thru your old ones too (at MMX) and I appreciate you also keeping them up, but these new ones are great. Python is fantastic as well, but the real gold of this channel is the ASM because it is EXTREMELY DIFFICULT to find good, modern video training on this. This is why I'm a patron of yours on Patreon.

    • @WhatsACreel
      @WhatsACreel  7 ปีที่แล้ว +6

      Cheers mate!

    • @WhatsACreel
      @WhatsACreel  7 ปีที่แล้ว +6

      Brilliant mate! The old vids will defo stay up. Thank you for your support, you're a legend!

  • @NewLondonMarshall
    @NewLondonMarshall ปีที่แล้ว

    Just found this tutorial series yesterday. I am a PHP developer so this is a big jump in difficulty but you're making it easier than anybody else could have! Thanks for making these videos!

  • @konstantinrebrov675
    @konstantinrebrov675 5 ปีที่แล้ว +39

    mov eax, eax doesn't work as a multi-byte nop because it zeroes the top 32 bits of rax! By nop you usually mean that the instruction has no side effects, and zeroing the top half of the register is a side effect.

    • @WhatsACreel
      @WhatsACreel  5 ปีที่แล้ว +28

      So true!! Did I say that? Whoops :) I wish YT still had annotations...

  • @Julia-ry6vo
    @Julia-ry6vo 2 ปีที่แล้ว +1

    Thank you! Your assembly tutorial is so clear. Now Assembly is not as dark magic as it was for me 😅

  • @dark_red_blood
    @dark_red_blood ปีที่แล้ว +1

    Thanks man, you have a good way of explaining

  • @mranthonymills
    @mranthonymills 2 ปีที่แล้ว

    I remember LEA as being mostly useful for arrays and quick math: LEA EBX, [Array + ECX*4] would calculate the address of your array location, where the array is of 32-bit ints and ECX has the index.

  • @FranciscoCrespoOM
    @FranciscoCrespoOM 7 ปีที่แล้ว +1

    Thank you for your vids! Easy to follow, clear, precise. This is really good assembly stuff. I look forward to seeing more on this series soon!

  • @speedracer9265
    @speedracer9265 ปีที่แล้ว

    Yeah, imma university student, that just want to know a lil' bit more
    And I want to say thank you! Your videos are kinda legendary!

  • @neilwalker3204
    @neilwalker3204 4 ปีที่แล้ว

    These videos are simply outstanding

  • @mranthonymills
    @mranthonymills 2 ปีที่แล้ว +1

    If you wonder: why XOR RAX, RAX instead of MOV RAX, 0? It's because the former is a much shorter instruction, since the latter has to include the whole 8-byte immediate value. Shorter code fits in instruction caches better.

  • @sabitkondakc9147
    @sabitkondakc9147 2 ปีที่แล้ว

    Man! you did wonders here ...

  • @victorfonseca7258
    @victorfonseca7258 3 ปีที่แล้ว

    Thanks for your videos! They're helping me a lot!

  • @walidkhames1966
    @walidkhames1966 11 หลายเดือนก่อน

    Thank you Creel.

  • @intelligentshitpastinginc
    @intelligentshitpastinginc 7 ปีที่แล้ว +6

    Are you going to continue the AES series? I'd like to know how AddRoundKey works for 192- and 256-bit keys

    • @WhatsACreel
      @WhatsACreel  7 ปีที่แล้ว +16

      My original AES series is finished. I never did 192, 256 or decryption. I find encryption depressing because it reminds me that we humans don't and can't trust each other. I would like to do some vids on the AES instruction set, if I find time, we will look at 192 and 256 in those vids. Cheers mate, thanks for watching!

  • @StevElmore
    @StevElmore 2 ปีที่แล้ว

    Computer hardware can multiply the values in two registers and give a double register product, using either signed or unsigned multiply instructions. I have looked for this capability in many high level languages but found none. Hence, large integer arithmetic must have some assembler code to achieve this efficiency. IBM 370, DEC PDP-11, and x86 processors all can do this ... because I did. I will compute large integer numbers on my 64 bit Windows desktop machine using C++ calling assembler code, and your videos.

  • @nezu_cc
    @nezu_cc 5 ปีที่แล้ว +1

    now i know what lea does, thanks

  • @homework8969
    @homework8969 4 หลายเดือนก่อน

    So the LEA instruction is quite simply just loading a REFERENCE of a value to the desired location and then to derefrence you could do something like MOV DI, byte ptr [SI] assuming that SI has a valid address.

    • @homework8969
      @homework8969 4 หลายเดือนก่อน

      wait nevermind the byte ptr [REGISTER] is the derefrence my bad.

  • @nandorbacso4625
    @nandorbacso4625 ปีที่แล้ว

    Wow this was awesome

  • @JohnMarkIsaacMadison
    @JohnMarkIsaacMadison 5 ปีที่แล้ว +1

    What is the difference between: mov rax, [foo] and lea rax, foo ?
    Also, isn't a register of a given name always at the same address?
    Because there is only one "rax".
    So: mov byte ptr[ rax ], 7 is just a type safe way of saying: move rax, 7 ?

    • @WhatsACreel
      @WhatsACreel  5 ปีที่แล้ว +4

      MOV moves a value, LEA loads an address. So after the "MOV", RAX would have the same value as whatever is at the address foo. So if "fo" was a variable with the value 10, then RAX would contain 10. After "LEA", RAX would contain the pointer foo itself, a memory address, like 0x0010DFA010, or whatever. It would contain the the address in memory of the foo variable; RAX would be a pointer pointing to foo.
      Registers don't have addresses. You're right, there's only one RAX exposed in ASM. On a low level, the CPU renames registers, and switches instructions around, to execute as much as it can at once. So the internal register the CPU uses when we say "RAX" is up to the CPU. It will only switch instructions and rename registers in such a way that it computes the correct answer. But it might be good to know that there really is no RAX; that's just a label we use in ASM. The actual register set is much larger; and it's in control of the CPU. It's not important if you're just starting ASM, but it's good to keep in the back of your mind.
      "MOV byte ptr [rax], 7" will move 7 into whatever RAX points to. So we if say LEA rax and foo, like we did before; then RAX points to foo. If we then say "MOV byte ptr [rax], 7", it will move 7 into foo. "MOV rax, 7", will move 7 into RAX. There's no type safety in ASM, other than operands being the correct size, there's no type safety. You can move a float into an DWORD, or add floating point doubles using the insteger ADD instruction, etc. The CPU doesn't care at all. Sounds silly, but that's half the fun of ASM :)
      Hope that was helpful. Cheers for watching :)

  • @EvanCarrollTheGreat
    @EvanCarrollTheGreat 6 ปีที่แล้ว

    Love it, really clean.

  • @nadavshemesh1231
    @nadavshemesh1231 4 ปีที่แล้ว +2

    Good stuff :)

    • @WhatsACreel
      @WhatsACreel  4 ปีที่แล้ว +1

      No worries mate! Cheers for watching :)

  • @stargazer7644
    @stargazer7644 ปีที่แล้ว

    I have never before heard move called mauve.

  • @robotronix420
    @robotronix420 6 ปีที่แล้ว

    Thank you very much!!! LIFESAVER

  • @allmycircuits8850
    @allmycircuits8850 4 ปีที่แล้ว

    I'm still confused that we can load immediate value into register using MOV, address is nothing more than a number, so THEORETICALLY we can load address of known place just as MOV with immediate value. I would argue MOV RAX, MyBte would do exactly that, while MOV RAX, [MyBte] would load value pointed by MyBte, but they did it the same and made it almost impossible to use MOV with immediate value for this purpose.

    • @xrafter
      @xrafter 4 ปีที่แล้ว

      So you want to get a value from address 56?
      Segmention fault (core dumped)

    • @allmycircuits8850
      @allmycircuits8850 4 ปีที่แล้ว

      @@xrafter No, I would like "MOV RAX, MyBte" to load address of MyBte into RAX, while "MOV al, [MyBte]" would load value from that address. It is perfectly possible in machine codes because address becomes known to translator or maybe linker. And putting some immediate value into register is perfectly OK with MOV. But somehow both these lines would mean the same...

    • @xrafter
      @xrafter 4 ปีที่แล้ว

      @@allmycircuits8850
      Will yes it will work but you need to give it a size for the assembler

    • @tomaspecl1082
      @tomaspecl1082 4 ปีที่แล้ว

      Assembler called "nasm" does that. When you do "mov rax, myByte" it will put adress of myByte into rax. When you use "mov rax, [myByte]" it will put value at adress myByte into rax. But for some reason the assembler "masm" he uses sees it as same. That is why I use nasm.

  • @amirhossein5055
    @amirhossein5055 2 ปีที่แล้ว

    excellent

  • @b213videoz
    @b213videoz 5 หลายเดือนก่อน

    5:20 can't you use offset ?
    mov al, OFFSET qwaral

  • @deckard5pegasus673
    @deckard5pegasus673 4 ปีที่แล้ว +1

    3:07 shouldn't "mov al, bittyye" be "mov al, [bittyye]' ? ... bittyye should have brackets?

  • @Cubinator73
    @Cubinator73 7 ปีที่แล้ว +2

    Is there any reason for padding code except for patching purpoes?

    • @WhatsACreel
      @WhatsACreel  7 ปีที่แล้ว +3

      It used to be recommended for optimization that we align tight loops to 16 bytes. I see no gain on my hardware, but it might be worth testing. It's also theoretically possible to control which execution units execute our instructions by cleverly inserting NOP. Whilst it's theoretically possible, I have not been able to manage it. Great question

    • @Cubinator73
      @Cubinator73 7 ปีที่แล้ว

      That sounds interesting. I definitely have to do some testing, when I have some time :)

    • @markteague8889
      @markteague8889 5 ปีที่แล้ว

      For performance reasons, data often needs to be word-aligned. This might not be as much of an issue with systems today having 64-bit data buses.

  • @honzabart12
    @honzabart12 4 ปีที่แล้ว +1

    Hello, i just wanted to ask, is there a way to move parts of 64 bit register into 2 32 bit registers ? Or work with selected bytes of that 64 bit register ?

    • @WhatsACreel
      @WhatsACreel  4 ปีที่แล้ว +1

      Yeah mate! If you have 64 bits in RDX, then you can move the low 32 into eax with "MOV EAX, EDX". Or you could move the upper 32 into EBX with SHRD or SHLD instructions. Can't remember the specifics of those instructions, but I'm pretty sure they'd do the trick! Otherwise you could just go "MOV RBX, RDX; SHR RBX, 32", move the data in 64 bits, then move it. You can also work with the smaller registers for RDX directly, without moving the data, but you have to be careful because a lot of instructions tht operate on 32 bit versions of the registers, i.e. EDX, will clear the top 32 bits of RDX!
      Well, hope this helps mate. I did a vid on registers somewhere. That might help too? Cheers for watching. Feel free to ask if you have any questions :)

    • @honzabart12
      @honzabart12 4 ปีที่แล้ว +3

      @@WhatsACreel Thanks mate :) u are a grade saver :)

    • @WhatsACreel
      @WhatsACreel  4 ปีที่แล้ว +1

      @@honzabart12 Welcome, good luck :)

  • @alpaka1337
    @alpaka1337 3 ปีที่แล้ว

    good vid :)

  • @iamtimsson
    @iamtimsson 9 หลายเดือนก่อน

    thankies

  • @董祥祥-v3t
    @董祥祥-v3t 5 ปีที่แล้ว

    (1)mov eax,dword ptr [p] (2) lea eax,[p]. which one is faster?? why? Thank you

    • @WhatsACreel
      @WhatsACreel  5 ปีที่แล้ว +3

      I think MOV is generally faster, tho it's probably hardware specific, and certainly worth testing if it's crucial. Agner Fog's instruction manual lists MOV as 0.5, and LEA as 1 for Skylake, so that's a pretty good hint (reciprocal throughput). Cheers for watching mate :)

  • @damiandassen7763
    @damiandassen7763 7 ปีที่แล้ว +10

    what is a creel?

    • @SirusStarTV
      @SirusStarTV 4 ปีที่แล้ว

      It's creel

    • @_Omni
      @_Omni 3 ปีที่แล้ว

      Google?

  • @diegonayalazo
    @diegonayalazo 3 ปีที่แล้ว

    Thanks

  • @founderofisis6627
    @founderofisis6627 6 ปีที่แล้ว

    mybyte: db 75
    lea rax, mybyte ; DONT WORK
    lea.asm:11: error: invalid combination of opcode and operands

    • @xmesaj2
      @xmesaj2 5 ปีที่แล้ว

      you got extra ":" in the .data where mybyte is

  • @insaneminer
    @insaneminer 3 ปีที่แล้ว

    are you from Australia?

  • @BGDMusic
    @BGDMusic 2 ปีที่แล้ว +2

    5:42 qwral is better

  • @TotalImmort7l
    @TotalImmort7l 3 ปีที่แล้ว +1

    I love this man.
    No homo tho.

  • @bocho8_
    @bocho8_ 2 ปีที่แล้ว

    tysm

  • @tecoberg
    @tecoberg 5 ปีที่แล้ว

    Which of them is faster?

    • @WhatsACreel
      @WhatsACreel  5 ปีที่แล้ว +1

      MOV is generally faster. Instruction speeds are hardware specific. On almost all hardware, "MOV reg, reg" is usually one of the fastest instructions of all. For memory reads, complex addressing, etc. the speeds of these instructions are all over the place; some MOV's are faster, some LEA's are faster. Anywho, cheers for watching :)

  • @Alex-op2kc
    @Alex-op2kc 3 ปีที่แล้ว

    Playlist: th-cam.com/play/PLKK11Ligqitg9MOX3-0tFT1Rmh3uJp7kA.html

  • @pavelsapehin4308
    @pavelsapehin4308 5 ปีที่แล้ว +1

    00:46 MOV
    04:15 LEA
    This table of content was created using "Smart Bookmarks for TH-cam" chrome extension. You can import and edit them using this extension. You can install it from the official Chrome Store Page (shortened link): smb.page.link/store

  • @IExSet
    @IExSet 3 ปีที่แล้ว

    Why they choosen so wordy syntax "byte ptr [smthg]" ? C-language syntax would be more convenient (byte*)rax, or byte*[rax].

  • @prim16
    @prim16 6 ปีที่แล้ว +1

    I learned in my class that MOV is written as source destination, and not destination source...

    • @WhatsACreel
      @WhatsACreel  6 ปีที่แล้ว +5

      It depends on which assembler you are using. I am using MASM, which uses the Intel syntax, "mov dest, src". But some assemblers (like GAS in linux programming), use the AT&T syntax, which is "mov src, dest".

    • @prim16
      @prim16 6 ปีที่แล้ว +1

      Understood, thank you :)

    • @markteague8889
      @markteague8889 5 ปีที่แล้ว +2

      It’s also different between the x86 family and Motorola 680x0 family. A Motorola 680x0 instruction such as MOVE.L (A6), D0 will move the long word (32-bits) at the address pointed to by address register 6 to data register 0. I kind of lament the abandonment of the MC680x0 family. Such a more elegant design than the kludgy x86-64 line of products.

  • @Spoif
    @Spoif 7 ปีที่แล้ว +1

    NOP DWORD ptr [AX + AX*1 + 00000000H] :)

    • @WhatsACreel
      @WhatsACreel  7 ปีที่แล้ว

      Oh great! Is this a multi-byte NOP? Which Assembler?

    • @freecrac
      @freecrac 7 ปีที่แล้ว

      AX ist not a valid address register.

  • @foxmulderqqs
    @foxmulderqqs 6 ปีที่แล้ว

    wtf brain burning

    • @WhatsACreel
      @WhatsACreel  6 ปีที่แล้ว +3

      Sorry, maybe Scully can help you, Fox