spi_nor 加解锁

static int stm_lock(struct spi_nor *nor, loff_t ofs, uint64_t len)

{

struct mtd_info *mtd = nor->mtd;

uint32_t offset = ofs;

uint8_t status_old, status_new;

int ret = 0;

status_old = read_sr(nor);

if (offset < mtd->size - (mtd->size / 2))

status_new = status_old | SR_BP2 | SR_BP1 | SR_BP0;

else if (offset < mtd->size - (mtd->size / 4))

status_new = (status_old & ~SR_BP0) | SR_BP2 | SR_BP1;

else if (offset < mtd->size - (mtd->size / 8))

status_new = (status_old & ~SR_BP1) | SR_BP2 | SR_BP0;

else if (offset < mtd->size - (mtd->size / 16))

status_new = (status_old & ~(SR_BP0 | SR_BP1)) | SR_BP2;

else if (offset < mtd->size - (mtd->size / 32))

status_new = (status_old & ~SR_BP2) | SR_BP1 | SR_BP0;

else if (offset < mtd->size - (mtd->size / 64))

status_new = (status_old & ~(SR_BP2 | SR_BP0)) | SR_BP1;

else

status_new = (status_old & ~(SR_BP2 | SR_BP1)) | SR_BP0;

/* Only modify protection if it will not unlock other areas */

if ((status_new & (SR_BP2 | SR_BP1 | SR_BP0)) >

(status_old & (SR_BP2 | SR_BP1 | SR_BP0))) {

write_enable(nor);

ret = write_sr(nor, status_new);

}

return ret;

}

static int stm_unlock(struct spi_nor *nor, loff_t ofs, uint64_t len)

{

struct mtd_info *mtd = nor->mtd;

uint32_t offset = ofs;

uint8_t status_old, status_new;

int ret = 0;

status_old = read_sr(nor);

if (offset+len > mtd->size - (mtd->size / 64))

status_new = status_old & ~(SR_BP2 | SR_BP1 | SR_BP0);

else if (offset+len > mtd->size - (mtd->size / 32))

status_new = (status_old & ~(SR_BP2 | SR_BP1)) | SR_BP0;

else if (offset+len > mtd->size - (mtd->size / 16))

status_new = (status_old & ~(SR_BP2 | SR_BP0)) | SR_BP1;

else if (offset+len > mtd->size - (mtd->size / 8))

status_new = (status_old & ~SR_BP2) | SR_BP1 | SR_BP0;

else if (offset+len > mtd->size - (mtd->size / 4))

status_new = (status_old & ~(SR_BP0 | SR_BP1)) | SR_BP2;

else if (offset+len > mtd->size - (mtd->size / 2))

status_new = (status_old & ~SR_BP1) | SR_BP2 | SR_BP0;

else

status_new = (status_old & ~SR_BP0) | SR_BP2 | SR_BP1;

/* Only modify protection if it will not lock other areas */

if ((status_new & (SR_BP2 | SR_BP1 | SR_BP0)) <

(status_old & (SR_BP2 | SR_BP1 | SR_BP0))) {

write_enable(nor);

ret = write_sr(nor, status_new);

}

return ret;

}

你可能感兴趣的:(spi_nor 加解锁)