dual_stores.c (1595B)
1/* 2 * Copyright(c) 2019-2021 Qualcomm Innovation Center, Inc. All Rights Reserved. 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation; either version 2 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, see <http://www.gnu.org/licenses/>. 16 */ 17 18#include <stdio.h> 19 20/* 21 * Make sure that two stores in the same packet honor proper 22 * semantics: slot 1 executes first, then slot 0. 23 * This is important when the addresses overlap. 24 */ 25static inline void dual_stores(int *p, char *q, int x, char y) 26{ 27 asm volatile("{\n\t" 28 " memw(%0) = %2\n\t" 29 " memb(%1) = %3\n\t" 30 "}\n" 31 :: "r"(p), "r"(q), "r"(x), "r"(y) 32 : "memory"); 33} 34 35typedef union { 36 int word; 37 char byte; 38} Dual; 39 40int err; 41 42static void check(Dual d, int expect) 43{ 44 if (d.word != expect) { 45 printf("ERROR: 0x%08x != 0x%08x\n", d.word, expect); 46 err++; 47 } 48} 49 50int main() 51{ 52 Dual d; 53 54 d.word = ~0; 55 dual_stores(&d.word, &d.byte, 0x12345678, 0xff); 56 check(d, 0x123456ff); 57 58 puts(err ? "FAIL" : "PASS"); 59 return err; 60}