@@ -478,6 +478,74 @@ pg_tde_write_one_map_entry(int fd, const TDEMapEntry *map_entry, off_t *offset,
478478#endif
479479
480480#ifndef FRONTEND
481+ static FILE *
482+ pg_tde_open_file_basic_copy (const char * tde_filename , const char * mode , bool ignore_missing )
483+ {
484+ FILE * file ;
485+
486+ file = AllocateFile (tde_filename , mode );
487+ if (file == NULL && !(errno == ENOENT && ignore_missing == true))
488+ {
489+ ereport (ERROR ,
490+ errcode_for_file_access (),
491+ errmsg ("could not open tde file \"%s\": %m" , tde_filename ));
492+ }
493+
494+ return file ;
495+ }
496+
497+ static void
498+ pg_tde_file_header_read_copy (const char * tde_filename , FILE * file , TDEFileHeader * fheader )
499+ {
500+ size_t bytes_read ;
501+
502+ Assert (fheader );
503+
504+ bytes_read = fread (fheader , TDE_FILE_HEADER_SIZE , 1 , file );
505+
506+ if (bytes_read != 1 || fheader -> file_version != PG_TDE_FILEMAGIC )
507+ {
508+ ereport (FATAL ,
509+ errcode_for_file_access (),
510+ errmsg ("TDE map file \"%s\" is corrupted %ld %d: %m" , tde_filename , bytes_read , fheader -> file_version ));
511+ }
512+ }
513+
514+ static FILE *
515+ pg_tde_open_file_write_copy (const char * tde_filename , const TDESignedPrincipalKeyInfo * signed_key_info )
516+ {
517+ FILE * file ;
518+ TDEFileHeader fheader ;
519+
520+ Assert (LWLockHeldByMeInMode (tde_lwlock_enc_keys (), LW_EXCLUSIVE ));
521+
522+ file = pg_tde_open_file_basic_copy (tde_filename , "rb+" , false);
523+
524+ pg_tde_file_header_read_copy (tde_filename , file , & fheader );
525+
526+ ///* In case it's a new file, let's add the header now. */
527+ //if (bytes_read == 0 && signed_key_info)
528+ // pg_tde_file_header_write(tde_filename, fd, signed_key_info, &bytes_written);
529+
530+ return file ;
531+ }
532+
533+ static bool
534+ pg_tde_read_one_map_entry_copy (FILE * map_file , TDEMapEntry * map_entry )
535+ {
536+ size_t entries_read ;
537+
538+ Assert (map_entry );
539+
540+ entries_read = fread (map_entry , MAP_ENTRY_SIZE , 1 , map_file );
541+
542+ /* We've reached the end of the file. */
543+ if (entries_read != 1 )
544+ return false;
545+
546+ return true;
547+ }
548+
481549/*
482550 * The caller must hold an exclusive lock on the key file to avoid
483551 * concurrent in place updates leading to data conflicts.
486554pg_tde_replace_key_map_entry (const RelFileLocator * rlocator , const InternalKey * rel_key_data , TDEPrincipalKey * principal_key )
487555{
488556 char db_map_path [MAXPGPATH ];
489- int map_fd ;
490- off_t curr_pos = 0 ;
557+ FILE * map_file ;
491558 off_t write_pos = 0 ;
492559 TDEMapEntry write_map_entry ;
493560 TDESignedPrincipalKeyInfo signed_key_Info ;
@@ -499,7 +566,7 @@ pg_tde_replace_key_map_entry(const RelFileLocator *rlocator, const InternalKey *
499566 pg_tde_sign_principal_key_info (& signed_key_Info , principal_key );
500567
501568 /* Open and validate file for basic correctness. */
502- map_fd = pg_tde_open_file_write (db_map_path , & signed_key_Info , false, & curr_pos );
569+ map_file = pg_tde_open_file_write_copy (db_map_path , & signed_key_Info );
503570
504571 /*
505572 * Read until we find an empty slot. Otherwise, read until end. This seems
@@ -509,32 +576,31 @@ pg_tde_replace_key_map_entry(const RelFileLocator *rlocator, const InternalKey *
509576 while (1 )
510577 {
511578 TDEMapEntry read_map_entry ;
512- off_t prev_pos = curr_pos ;
513579
514- if (!pg_tde_read_one_map_entry ( map_fd , & read_map_entry , & curr_pos ))
580+ if (!pg_tde_read_one_map_entry_copy ( map_file , & read_map_entry ))
515581 {
516582 if (write_pos == 0 )
517- write_pos = prev_pos ;
583+ write_pos = ftell ( map_file ) ;
518584 break ;
519585 }
520586
521587 if (read_map_entry .spcOid == rlocator -> spcOid && read_map_entry .relNumber == rlocator -> relNumber )
522588 {
523- write_pos = prev_pos ;
589+ write_pos = ftell ( map_file ) - MAP_ENTRY_SIZE ;
524590 break ;
525591 }
526592
527593 if (write_pos == 0 && read_map_entry .type == MAP_ENTRY_TYPE_EMPTY )
528- write_pos = prev_pos ;
594+ write_pos = ftell ( map_file ) - MAP_ENTRY_SIZE ;
529595 }
530596
531597 /* Initialize map entry and encrypt key */
532598 pg_tde_initialize_map_entry (& write_map_entry , principal_key , rlocator , rel_key_data );
533599
534600 /* Write the given entry at curr_pos; i.e. the free entry. */
535- pg_tde_write_one_map_entry (map_fd , & write_map_entry , & write_pos , db_map_path );
601+ pg_tde_write_one_map_entry (fileno ( map_file ) , & write_map_entry , & write_pos , db_map_path );
536602
537- CloseTransientFile ( map_fd );
603+ FreeFile ( map_file );
538604}
539605#endif
540606
0 commit comments