1*86e5e429SRamon Fried // SPDX-License-Identifier: GPL-2.0+ 2*86e5e429SRamon Fried /* 3*86e5e429SRamon Fried * Miscellaneous Snapdragon functionality 4*86e5e429SRamon Fried * 5*86e5e429SRamon Fried * (C) Copyright 2018 Ramon Fried <ramon.fried@gmail.com> 6*86e5e429SRamon Fried * 7*86e5e429SRamon Fried */ 8*86e5e429SRamon Fried 9*86e5e429SRamon Fried #include <common.h> 10*86e5e429SRamon Fried #include <mmc.h> 11*86e5e429SRamon Fried #include <asm/arch/misc.h> 12*86e5e429SRamon Fried 13*86e5e429SRamon Fried /* UNSTUFF_BITS macro taken from Linux Kernel: drivers/mmc/core/sd.c */ 14*86e5e429SRamon Fried #define UNSTUFF_BITS(resp, start, size) \ 15*86e5e429SRamon Fried ({ \ 16*86e5e429SRamon Fried const int __size = size; \ 17*86e5e429SRamon Fried const u32 __mask = (__size < 32 ? 1 << __size : 0) - 1; \ 18*86e5e429SRamon Fried const int __off = 3 - ((start) / 32); \ 19*86e5e429SRamon Fried const int __shft = (start) & 31; \ 20*86e5e429SRamon Fried u32 __res; \ 21*86e5e429SRamon Fried \ 22*86e5e429SRamon Fried __res = resp[__off] >> __shft; \ 23*86e5e429SRamon Fried if (__size + __shft > 32) \ 24*86e5e429SRamon Fried __res |= resp[__off - 1] << ((32 - __shft) % 32); \ 25*86e5e429SRamon Fried __res & __mask; \ 26*86e5e429SRamon Fried }) 27*86e5e429SRamon Fried 28*86e5e429SRamon Fried u32 msm_board_serial(void) 29*86e5e429SRamon Fried { 30*86e5e429SRamon Fried struct mmc *mmc_dev; 31*86e5e429SRamon Fried 32*86e5e429SRamon Fried mmc_dev = find_mmc_device(0); 33*86e5e429SRamon Fried if (!mmc_dev) 34*86e5e429SRamon Fried return 0; 35*86e5e429SRamon Fried 36*86e5e429SRamon Fried return UNSTUFF_BITS(mmc_dev->cid, 16, 32); 37*86e5e429SRamon Fried } 38