home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 5 Edit / 05-Edit.zip / p2demo21.exe / PEL / LOCKS.PEL < prev    next >
Text File  |  1995-03-14  |  19KB  |  609 lines

  1. # $Header:   P:\source\wmacros\locks.pev   1.18   14 Mar 1995 08:28:34   NOBLE  $
  2.  
  3. ##############################################################################
  4. #
  5. #       Compuware Corporation
  6. #         31440 Northwestern Highway
  7. #           Farmington Hills, Michigan 48334-2564
  8. #
  9. #   This source code listing contains information that is
  10. #   proprietary to Compuware Corporation and may not be copied
  11. #   duplicated, translated, transmitted, stored, retrieved
  12. #   or in any manner or by any method conveyed or disclosed
  13. #   to a third party or parties without express written
  14. #   permission from Compuware Corporation.
  15. #
  16. #  
  17. ##############################################################################
  18.  
  19. #### $Workfile:   locks.pel  $: file locking mechanism
  20.  
  21. local IDL_FILE_TYPE_LIST         = 102
  22. local IDR_FILE_COPY_ON_MOD       = 1532
  23. local IDR_FILE_COPY_ON_OPEN      = 1533
  24. local IDR_FILE_COPY_NO_ACTION    = 1534
  25.  
  26. local IDC_FILE_LOCK_ON_MOD       = 1531
  27.  
  28. local IDD_FILE_PAGE              = 1530
  29.  
  30. local locked_filenames[];     # List of all semaphore file names 
  31.                #   to be deleted upon exit
  32.  
  33. local file_locking_enabled = 0;         # File locking is enabled
  34.  
  35. local file_locking_cleanup_enabled = 0; # File locking has been enabled and 
  36.                                         #    cleanup needs to occur upon exit
  37.  
  38. local LOCKED_EXT_CHAR   = "&" # extension character for locking files
  39.  
  40.  
  41. ## toggle_file_locking()
  42. #
  43. #  Enable or disable the ability to lock files.
  44. #
  45. global function toggle_file_locking( on ) {
  46.  
  47.    if( argcount() < 1 )
  48.       on = !file_locking_enabled;
  49.    else
  50.       on = 0+on
  51.    if (on)
  52.       enable_file_locking();
  53.    else
  54.       disable_file_locking();
  55. }
  56.  
  57. ## enable_file_locking()
  58. #
  59. #  Enable file locking by attaching an event handler which will be called
  60. #  every time a new file is about to be edited.
  61. #
  62. #  Also attach an event handler to cleanup all locked files upon exit.
  63. #
  64. local function enable_file_locking(){
  65.    if (!file_locking_enabled) {
  66.       # need a handler to create semaphore files for
  67.       # each file edited.
  68.       #
  69.       attach_event_handler( EVENT.NEW_EDIT_FILE, \
  70.          function_id( "lock_edit_file" ));
  71.  
  72.       # need a handler to cleanup a semaphore files
  73.       #
  74.       if (!file_locking_cleanup_enabled) {
  75.          attach_event_handler( EVENT.EXIT_EDITOR, \
  76.             function_id( "unlock_edit_files" ));
  77.          file_locking_cleanup_enabled = 1;
  78.       }
  79.    }
  80. }
  81.  
  82. ## disable_file_locking()
  83. #
  84. #  Disable file locking by deleting the event handler attached to the
  85. #  NEW_EDIT_FILE event.
  86. #
  87. local function disable_file_locking(){
  88.    if (file_locking_enabled) {
  89.       delete_event( EVENT.NEW_EDIT_FILE, \
  90.          function_id( "lock_edit_file" ));
  91.    }
  92. }
  93.  
  94.  
  95. ## lock_edit_file()
  96. #
  97. #  This function is attached to the NEW_EDIT_FILE event and is called
  98. #  for every file that is about to be loaded into the system either
  99. #  through edit_file() or create_buffer().
  100. #
  101. #  This function only allows locking of non-SYSTEM buffers because multiple
  102. #  system buffers may need to be created without locking.
  103. #
  104. #  Locking is obtained by taking the original filename and modifying the
  105. #  extension.  If the new filename exists in the original directory, then
  106. #  the file is assummed to be locked and an error is generated.  If the
  107. #  file can be created, it is and the original file is considered locked.
  108. #  If the new filename cannot be created, the original directory is assummed
  109. #  to be read-only and can't be written to anyway, so why lock it.
  110. #
  111.  
  112. global function lock_edit_file(){
  113.    local fname;
  114.    local fid;
  115.    local bname = buffer_original_filename;
  116.    local pbuf = current_buffer;
  117.    local prev_pe = pause_on_error;
  118.  
  119.  
  120.  
  121.    if ((buffer_original_filename) && (!and(buffer_flags, BUFFER_SYSTEM))){
  122.       while (next_buffer( "", 1 ) != pbuf) {
  123.          if ((buffer_original_filename == bname) \
  124.             && (!and(buffer_flags, BUFFER_SYSTEM))){
  125.             current_buffer = pbuf;
  126.             return;
  127.          }
  128.       }
  129.  
  130.       current_buffer = pbuf;
  131.  
  132.       #
  133.       # only worry about locking non-system buffer files
  134.       #
  135.       fname = create_semaphore_fname( bname = buffer_original_filename, \
  136.          LOCKED_EXT_CHAR );
  137.  
  138.       if (fname == bname){
  139.          # We are trying to edit one of the semaphore files.
  140.          # Could have been called to edit x.* and x.__& was
  141.          # created and found before findnext() was done.
  142.          # Just ignore the file for now.
  143.          buffer_filename = "";
  144.          return;
  145.       } else if (filetime( fname )) {
  146.          # the file exists so it must be locked by
  147.          # another user.
  148.  
  149.  
  150.          pause_on_error = 1;
  151.          buffer_flags = or( buffer_flags, BUFFER_READ_ONLY )
  152.          warning( "File `" bname "' already locked, loaded as read-only buffer." );
  153.          pause_on_error = prev_pe;
  154.          return;
  155.  
  156.  
  157.          ## uncomment the next 2 lines and comment the 
  158.          ## previous 5 lines to prevent multiple 
  159.          ## users from seeing the same file
  160.  
  161.          # buffer_filename = "";
  162.          # error( "File `" bname "' already locked." );
  163.  
  164.  
  165.       } else {
  166.          fid = fopen( fname, 1 )    # open for Write only
  167.          if (fid == -1){         # error occurred
  168.             if (filetime( fname )){ # created by another user
  169.                # the file exists so it must be locked by
  170.                # another user.
  171.  
  172.  
  173.                pause_on_error = 1;
  174.                buffer_flags = or( buffer_flags, BUFFER_READ_ONLY )
  175.                warning( "File `" bname "' locked, buffer is read-only." );
  176.                pause_on_error = prev_pe;
  177.                return;
  178.  
  179.                ## uncomment the next 2 lines and comment the 
  180.                ## previous 5 lines to prevent multiple 
  181.                ## users from seeing the same file
  182.  
  183.  
  184.                # buffer_filename = "";
  185.                # error( "File `" bname "' already locked." );
  186.             } else {
  187.                # can't open file so must be 
  188.                # read-only directory
  189.                return;
  190.             }
  191.          } else {
  192.             #
  193.             # the file is now open
  194.             # save the name so we can delete it when the
  195.             # file is closed
  196.             #
  197.             locked_filenames[ fname ] = 0;
  198.             fclose( fid );
  199.          }
  200.       }
  201.    }
  202. }
  203.  
  204.  
  205. ## unlock_edit_files()
  206. #
  207. #  All files which have been locked are unlocked by deleting the associated
  208. #  semaphore file.
  209. #
  210. global function unlock_edit_files(){
  211.    local fn
  212.  
  213.    for (fn in locked_filenames){
  214.       unlink( fn );
  215.    }
  216. }
  217.  
  218. ## unlock_file()
  219. #
  220. #  All files which have been locked are unlocked by deleting the associated
  221. #  semaphore file.
  222. #
  223. global function unlock_file( fn ){
  224.    fn = create_semaphore_fname( fn, LOCKED_EXT_CHAR );
  225.  
  226.    if (fn in locked_filenames){
  227.       unlink( fn );
  228.       delete( locked_filenames[ fn ] );
  229.    }
  230. }
  231.  
  232.  
  233. ################################################################################
  234. #  
  235. #  Files section of the notebook
  236. #  
  237. ################################################################################
  238.  
  239. local dhAccessSettings = 0;
  240. local phAccessSettings = 0;
  241. local dhFileWindowSettings = 0;
  242. local phFileWindowSettings = 0;
  243.  
  244. global function file_settings_notebook(dlgid)
  245. {
  246.    local dhHelpSettings, phHelpSettings;
  247.  
  248.    nb_initializing = TRUE;
  249.  
  250.    if (dlgid)
  251.    {
  252.       if(status_bar_flags )
  253.          message( "Creating File Settings pages..." );
  254.  
  255.       # Add the pages to the notebook
  256.       #
  257.       phHelpSettings = append_notebook_page( dlgid, dhHelpSettings,
  258.                                            " ",
  259.                                            "File", NBTAB_MAJOR )
  260.    
  261.       nbPagePrefix[phHelpSettings].name = "filehelp";
  262.       #  create_edithelp_page(phHelpSettings, dlgid);
  263.  
  264.       phAccessSettings = append_notebook_page(dlgid, dhAccessSettings,
  265.                                           " File Locking and Virtual Memory",
  266.                                           "Access", NBTAB_MINOR )
  267.       nbPagePrefix[phAccessSettings].name = "access";
  268.  
  269. #      phFileWindowSettings = append_notebook_page(dlgid, dhFileWindowSettings,
  270. #                                          " Files in windows",
  271. #                                          "Windows", NBTAB_MINOR )
  272. #
  273. #      nbPagePrefix[phAccessSettings].name = "access";
  274. #      nbPagePrefix[phFileWindowSettings].name = "file_window";
  275.  
  276.    }
  277.    else
  278.    {
  279.       warning("Illegal call to file_settings_notebook()");
  280.    }
  281.  
  282.    nb_initializing = FALSE;
  283. }
  284.                                      
  285. global function reset_file_settings_notebook()
  286. {
  287.    dhAccessSettings  = 0
  288.  
  289.    phAccessSettings  = 0
  290.  
  291.    dhFileWindowSettings  = 0
  292.  
  293.    phFileWindowSettings  = 0
  294. }
  295.  
  296. global function create_filehelp_page(pageid, dlgid)
  297. {
  298.    local dhHelpSettings;
  299.  
  300.    dhHelpSettings = create_page(function_id( "nop_settings_callback"), 
  301.                                 dlgid, IDD_FILE_HELP_PAGE, resource_dll );
  302.    attach_help(editor_helpfile, dhHelpSettings);
  303.    
  304.    if ( isWindows() )
  305.       nbPagePrefix[pageid].help = "File Help Page";
  306.    else
  307.       nbPagePrefix[pageid].help = "filehelppage";
  308.       
  309.    set_notebook_page_dialog(dlgid, pageid, dhHelpSettings);
  310.    nbPagePrefix[pageid].dialog_handle = dhHelpSettings;
  311. }
  312.  
  313. global function create_access_page(pageid, dlgid)
  314. {
  315.    dhAccessSettings = create_page(function_id( "access_settings_callback" ), 
  316.                                 dlgid, IDD_FILE_PAGE, resource_dll )
  317.                                 
  318.    add_dialog_item( dhAccessSettings, IDB_UNDO, DCTRL_PUSH_BUTTON )
  319.    attach_help(editor_helpfile, dhAccessSettings);
  320.    
  321.    if ( isWindows() )
  322.       nbPagePrefix[pageid].help = "File Access Page";
  323.    else
  324.       nbPagePrefix[pageid].help = "fileaccesspage";
  325.       
  326.    set_dialog_item( dhAccessSettings, IDL_FILE_TYPE_LIST, DAC_ADD_ITEM, "LAN files")
  327.    set_dialog_item( dhAccessSettings, IDL_FILE_TYPE_LIST, DAC_ADD_ITEM, "Local files")
  328.    set_dialog_item( dhAccessSettings, IDL_FILE_TYPE_LIST, DAC_ADD_ITEM, "Floppy files")
  329.  
  330.    set_dialog_item( dhAccessSettings, IDL_FILE_TYPE_LIST, DAC_SELECT_INDEX, 0 )
  331.  
  332.    initialize_access_settings( dhAccessSettings )
  333.    set_notebook_page_dialog(dlgid, pageid, dhAccessSettings);
  334.    nbPagePrefix[pageid].dialog_handle = dhAccessSettings;
  335.    set_dialog_item( dhAccessSettings, IDB_UNDO, DAC_DISABLE)
  336. }
  337.  
  338. #global function create_file_window_page(pageid, dlgid)
  339. #{
  340. #   dhFileWindowSettings = create_page(function_id( "file_window_settings_callback" ), 
  341. #                                      dlgid, IDD_FILE_WINDOW_PAGE, resource_dll )
  342. #                                
  343. #   add_dialog_item( dhFileWindowSettings, IDB_UNDO, DCTRL_PUSH_BUTTON )
  344. #   attach_help(editor_helpfile, dhFileWindowSettings);
  345. #   
  346. #   if ( isWindows() )
  347. #      nbPagePrefix[pageid].help = "File Window Page";
  348. #   else
  349. #      nbPagePrefix[pageid].help = "filewindowpage";
  350. #      
  351. #
  352. #   initialize_file_window_settings( dhFileWindowSettings )
  353. #   set_notebook_page_dialog(dlgid, pageid, dhFileWindowSettings);
  354. #   nbPagePrefix[pageid].dialog_handle = dhFileWindowSettings;
  355. #
  356. #   set_dialog_item( dhFileWindowSettings, IDB_UNDO, DAC_DISABLE)
  357. #}
  358.  
  359. local lock_files[]
  360.  
  361. local function initialize_access_settings(handle)
  362. {
  363.    lock_files[0].lock = lock_lan_files_on_mod
  364.    lock_files[0].copy = copy_lan_files_on_action
  365.  
  366.    lock_files[1].lock = lock_local_files_on_mod
  367.    lock_files[1].copy = copy_local_files_on_action
  368.  
  369.    lock_files[2].lock = lock_floppy_files_on_mod
  370.    lock_files[2].copy = copy_floppy_files_on_action
  371.  
  372.    initialize_file_type(handle)
  373. }
  374.  
  375. local function initialize_file_type(handle)
  376. {
  377.    local type = query_dialog_item( handle, IDL_FILE_TYPE_LIST, DAC_SELECT_INDEX )
  378.  
  379.    if ( lock_files[type].lock )
  380.       set_dialog_item( handle, IDC_FILE_LOCK_ON_MOD, DAC_CHECK )
  381.    else
  382.       set_dialog_item( handle, IDC_FILE_LOCK_ON_MOD, DAC_UNCHECK )
  383.    
  384.    if ( lock_files[type].copy == "mod" )
  385.    {
  386.       set_dialog_item( handle, IDR_FILE_COPY_ON_MOD, DAC_CHECK )
  387.       set_dialog_item( handle, IDR_FILE_COPY_ON_OPEN, DAC_UNCHECK )
  388.       set_dialog_item( handle, IDR_FILE_COPY_NO_ACTION, DAC_UNCHECK )
  389.    }
  390.    else if ( lock_files[type].copy == "open" )
  391.    {
  392.       set_dialog_item( handle, IDR_FILE_COPY_ON_MOD, DAC_UNCHECK )
  393.       set_dialog_item( handle, IDR_FILE_COPY_ON_OPEN, DAC_CHECK )
  394.       set_dialog_item( handle, IDR_FILE_COPY_NO_ACTION, DAC_UNCHECK )
  395.    }
  396.    else
  397.    {
  398.       set_dialog_item( handle, IDR_FILE_COPY_ON_MOD, DAC_UNCHECK )
  399.       set_dialog_item( handle, IDR_FILE_COPY_ON_OPEN, DAC_UNCHECK )
  400.       set_dialog_item( handle, IDR_FILE_COPY_NO_ACTION, DAC_CHECK )
  401.    }
  402. }
  403.  
  404. global function undo_access_settings(handle)
  405. {
  406.    initialize_access_settings(handle)
  407. }
  408.  
  409. global function access_settings_callback()
  410. {
  411.    local handle  = callback_dialog_handle
  412.    local ret_msg = DRC_CONTINUE;
  413.    local type
  414.  
  415.    if(callback_msg == DM_HELPREQUESTED)
  416.    {   
  417.       display_help(nbPagePrefix[current_nb_page].help, handle);
  418.       return DRC_MSG_PROCESSED;
  419.    }
  420.    else if(callback_msg == DM_CANCEL )
  421.    {
  422.        return DRC_MSG_PROCESSED
  423.    }
  424.    else if ( callback_msg == DM_SELECT )
  425.    {
  426.       initialize_file_type(handle)
  427.    }
  428.    else if((callback_msg == DM_CLICK) || (callback_msg == DM_DOUBLE_CLICK) )
  429.    {
  430.       if(callback_index == IDB_UNDO  ) 
  431.       {
  432.          undo_access_settings(handle);
  433.          set_dialog_item( handle, IDB_UNDO, DAC_DISABLE)
  434.          return DRC_MSG_PROCESSED
  435.       }
  436.       else if( callback_index == IDB_DEFAULT  ) 
  437.       {
  438.          nbPagePrefix[current_nb_page].modified = TRUE;
  439.          default_access_settings(handle);
  440.          return DRC_MSG_PROCESSED
  441.       }
  442.       else 
  443.       {
  444.          set_dialog_item( handle, IDB_UNDO, DAC_ENABLE)
  445.          type = query_dialog_item( handle, IDL_FILE_TYPE_LIST, DAC_SELECT_INDEX )
  446.          nbPagePrefix[current_nb_page].modified = TRUE;
  447.  
  448.          if ( callback_index == IDR_FILE_COPY_ON_MOD )
  449.             lock_files[type].copy = "mod"
  450.          else if ( callback_index == IDR_FILE_COPY_ON_OPEN )
  451.             lock_files[type].copy = "open"
  452.          else if ( callback_index == IDR_FILE_COPY_NO_ACTION )
  453.             lock_files[type].copy = ""
  454.          else if ( callback_index == IDC_FILE_LOCK_ON_MOD )
  455.             lock_files[type].lock = query_dialog_item( handle, callback_index, DAC_CHECK )
  456.       }
  457.    }
  458.  
  459.    return ret_msg;
  460. }
  461.  
  462. #local function initialize_file_window_settings( handle )
  463. #{
  464. #   if ( mdi_mode )
  465. #   {
  466. #      set_dialog_item( handle, 102, DAC_HIDE )
  467. #
  468. #      if ( create_new_bufwin )
  469. #         set_dialog_item(handle, IDC_OPEN_FILES_IN_WINDOW, DAC_CHECK )
  470. #      else
  471. #         set_dialog_item(handle, IDC_OPEN_FILES_IN_WINDOW, DAC_UNCHECK )
  472. #
  473. #      if ( query_bind_buff_to_win() )
  474. #         set_dialog_item(handle, IDC_CLOSE_BUFFER_WINDOW, DAC_CHECK )
  475. #      else
  476. #         set_dialog_item(handle, IDC_CLOSE_BUFFER_WINDOW, DAC_UNCHECK )
  477. #   }
  478. #   else
  479. #   {
  480. #      set_dialog_item( handle, 102, DAC_SHOW )
  481. #      set_dialog_item(handle, IDC_OPEN_FILES_IN_WINDOW, DAC_DISABLE )
  482. #      set_dialog_item(handle, IDC_CLOSE_BUFFER_WINDOW, DAC_DISABLE )
  483. #      set_dialog_item(handle, IDB_DEFAULT, DAC_DISABLE )
  484. #   }
  485. #}
  486. #
  487. #global function undo_file_window_settings(handle)
  488. #{
  489. #   initialize_file_window_settings(handle)
  490. #}
  491. #
  492. #global function default_file_window_settings(handle)
  493. #{
  494. #   if ( mdi_mode )
  495. #   {
  496. #      set_dialog_item(handle, IDC_OPEN_FILES_IN_WINDOW, DAC_UNCHECK )
  497. #      set_dialog_item(handle, IDC_CLOSE_BUFFER_WINDOW, DAC_UNCHECK )
  498. #   }
  499. #   else
  500. #   {
  501. #      set_dialog_item(handle, IDC_OPEN_FILES_IN_WINDOW, DAC_DISABLE )
  502. #      set_dialog_item(handle, IDC_CLOSE_BUFFER_WINDOW, DAC_DISABLE )
  503. #   }
  504. #}
  505. #
  506. #global function file_window_settings_callback()
  507. #{
  508. #   local handle  = callback_dialog_handle
  509. #   local ret_msg = DRC_CONTINUE;
  510. #
  511. #   if(callback_msg == DM_HELPREQUESTED)
  512. #   {   
  513. #      display_help(nbPagePrefix[current_nb_page].help, handle);
  514. #      return DRC_MSG_PROCESSED;
  515. #   }
  516. #   else if(callback_msg == DM_CANCEL )
  517. #   {
  518. #       return DRC_MSG_PROCESSED
  519. #   }
  520. #   else if((callback_msg == DM_CLICK) || (callback_msg == DM_DOUBLE_CLICK) )
  521. #   {
  522. #      if(callback_index == IDB_UNDO  ) 
  523. #      {
  524. #         nbPagePrefix[current_nb_page].modified = FALSE;
  525. #         undo_file_window_settings(handle);
  526. #         set_dialog_item( handle, IDB_UNDO, DAC_DISABLE)
  527. #         return DRC_MSG_PROCESSED
  528. #      }
  529. #      else if( callback_index == IDB_DEFAULT  ) 
  530. #      {
  531. #         nbPagePrefix[current_nb_page].modified = TRUE;
  532. #         default_file_window_settings(handle);
  533. #         return DRC_MSG_PROCESSED
  534. #      }
  535. #      else if( callback_index == IDC_OPEN_FILES_IN_WINDOW || callback_index == IDC_CLOSE_BUFFER_WINDOW )
  536. #      {
  537. #         nbPagePrefix[current_nb_page].modified = TRUE;
  538. #         set_dialog_item( handle, IDB_UNDO, DAC_ENABLE)
  539. #      }
  540. #   }
  541. #
  542. #   return ret_msg;
  543. #}
  544.  
  545. global function assign_access_changes(handle)
  546. {
  547.    toggle_lock_lan_files_on_mod( lock_files[0].lock )
  548.    toggle_lock_local_files_on_mod( lock_files[1].lock )
  549.    toggle_lock_floppy_files_on_mod( lock_files[2].lock )
  550.  
  551.    copy_lan_files_on( lock_files[0].copy )
  552.    copy_local_files_on( lock_files[1].copy )
  553.    copy_floppy_files_on( lock_files[2].copy )
  554. }
  555.  
  556. #global function assign_file_window_changes(handle)
  557. #{
  558. #   local ofiw  = query_dialog_item( handle, IDC_OPEN_FILES_IN_WINDOW, DAC_CHECK )
  559. #   local prev_setting = create_new_bufwin;
  560. #   local new_setting = ofiw;
  561. #   local first, cb, list;
  562. #   local first_window = current_window;
  563. #
  564. #   toggle_create_new_win( ofiw )
  565. #
  566. #   ofiw  = query_dialog_item( handle, IDC_CLOSE_BUFFER_WINDOW, DAC_CHECK )
  567. #   prev_setting = (prev_setting && query_bind_buff_to_win());
  568. #   new_setting  = (new_setting && ofiw);
  569. #   toggle_bind_buff_to_win( ofiw )
  570. #
  571. #   #  If the user turned the feature on, put each buffer in it's own window;
  572. #   cascade_buffers();
  573. ##   if(new_setting && !prev_setting)
  574. ##   {
  575. ##      first = current_buffer;
  576. ##      cb = next_buffer();
  577. ##
  578. ##      #  Save each buffer filename in a list (create_buf_and_win didn't work
  579. ##      #  if the buffer we open is current;
  580. ##      while(cb != first)
  581. ##      {
  582. ##         list[buffer_filename] = TRUE;
  583. ##         cb = next_buffer();
  584. ##      }
  585. ##      cb = FALSE;
  586. ##
  587. ##      #  Attach each buffer in the list to its own window;
  588. ##      for(cb in list)
  589. ##         create_buf_and_win(cb);
  590. ##   }
  591. #   #  I go back to the first window because there is a busy cursor there
  592. #   #  and the cursor won't be reset unless the notebook finishes processing
  593. #   #  with this window current;
  594. #   current_window = first_window;
  595. #}
  596.  
  597.  
  598. global function default_access_settings(handle)
  599. {
  600.    lock_files[0].lock = 0
  601.    lock_files[0].copy = ""
  602.    lock_files[1].lock = 0
  603.    lock_files[1].copy = ""
  604.    lock_files[2].lock = 0
  605.    lock_files[2].copy = ""
  606.  
  607.    initialize_file_type(handle)
  608. }
  609.