cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

cmpxchg16b_emu.S (1007B)


      1/* SPDX-License-Identifier: GPL-2.0-only */
      2#include <linux/linkage.h>
      3#include <asm/percpu.h>
      4
      5.text
      6
      7/*
      8 * Inputs:
      9 * %rsi : memory location to compare
     10 * %rax : low 64 bits of old value
     11 * %rdx : high 64 bits of old value
     12 * %rbx : low 64 bits of new value
     13 * %rcx : high 64 bits of new value
     14 * %al  : Operation successful
     15 */
     16SYM_FUNC_START(this_cpu_cmpxchg16b_emu)
     17
     18#
     19# Emulate 'cmpxchg16b %gs:(%rsi)' except we return the result in %al not
     20# via the ZF.  Caller will access %al to get result.
     21#
     22# Note that this is only useful for a cpuops operation.  Meaning that we
     23# do *not* have a fully atomic operation but just an operation that is
     24# *atomic* on a single cpu (as provided by the this_cpu_xx class of
     25# macros).
     26#
     27	pushfq
     28	cli
     29
     30	cmpq PER_CPU_VAR((%rsi)), %rax
     31	jne .Lnot_same
     32	cmpq PER_CPU_VAR(8(%rsi)), %rdx
     33	jne .Lnot_same
     34
     35	movq %rbx, PER_CPU_VAR((%rsi))
     36	movq %rcx, PER_CPU_VAR(8(%rsi))
     37
     38	popfq
     39	mov $1, %al
     40	RET
     41
     42.Lnot_same:
     43	popfq
     44	xor %al,%al
     45	RET
     46
     47SYM_FUNC_END(this_cpu_cmpxchg16b_emu)