You will need to consult the datasheet heavily to do what you are attempting. This paragraph from the datasheet confirms some of the previous answers:
ATmega88PA, ATmega168PA and ATmega328P support a real Read-While-Write Self-Programming
mechanism. There is a separate Boot Loader Section, and the SPM instruction can
only execute from there. In ATmega48PA, there is no Read-While-Write support and no separate
Boot Loader Section. The SPM instruction can execute from the entire Flash.
So: on an Atmega328 you can ONLY write to flash from within the bootloader section.
The largest boot loader section you can have is 2048 bytes. (also confirmed in the datasheet)
My suggestion would be: Write your own "Boot Loader" that reads from serial and writes to flash, similar to the arduino bootloader, and also allow to read from flash via serial. Then program this onto a secondary atmega328 processor, and and use your arduino to read and write the flash (via serial) in the secondary processor.
Keep in mind that the flash memory only have a 10,000 write cycle endurance.