Placing a key variable in internal flash Memory
secretkey.c:

const long secret_key[3] __attribute__((used)) = {0xABABABAB,0xCDCDCDCD, 0xEFEFEFEF};


__attribute__((used)) to prevent it from being removed if it isn't used anywhere.

secretkey.h:

extern const long secret_key[3];


scatterfile.sct:
Make a region and a C file, then add the RO (read only) part of that C file to the region. Nothing else.

; *************************************************************
; *** Scatter-Loading Description File generated by uVision ***
; *************************************************************

LR_IROM1 0x08000000 0x00002000 {    ; load region size_region
  ER_IROM1 0x08000000 0x00002000  {  ; load address = execution address
   *.o (RESET, +First)
   *(InRoot$$Sections)
   .ANY (+RO)
  }

  RW_IRAM1...
}

LR_SECRET_IROM1 0x08002000 0x00000030  {                         
  SECRET_IROM1 0x08002000 0x00000030  {
    secretkey.o (+RO)
  }
}


You now have two load regions (lr_), these blocks of memory (regions) are programmed into flash by the programmer. LR_IROM1 and LR_SECRET_IROM1.
Inside the load regions are execution regions. This is where the code references the objects from. ER_IROM1, RW_IRAM1 and SECRET_IROM1. 

Most often the addresses of the load and execution region are identical.
But you can have a load region for flash, and an execution region for sram.
For example with pre-initialized variables. This means the linker then must insert the scatter loading algorithm. This copies the data from the flash location where the data is programmed in flash, to the intended usable location in sram. (i.e. where the code thinks the variables are)

This algorithm is called from the startup.s file, and it makes the jump to int main(void), for Keil this algorithm is started by calling __main in startup.s.

But when the execution region already equals the load region, no copying is required. Such as with the actual code, and your now with constant.  

In my earlier version (and the part in your question), the constant was put inside an execution region, meaning it was programmed using .ANY (+RO) and then copied to the intended location. Except the code can't write to flash, thus nothing would be changed there. 

See also, ARM® Compiler armlink User Guide: 8.2 Syntax of a scatter file
I'd also recommend looking at the memory .map file the linker outputs. You can use it to verify how your image is put together. I made a small tool for this.
The tickbox is in target settings -&gt; listing -&gt; linker listing.



Your RAM regions are a bit strange. I do not think there is an advantage in using multiple 256 sized regions.   

Instead, you could use all SRAM regions:
- 96 kByte at 0x20000000
- 32 kByte at 0x10000000