Windows long path experimenting report

Adrian Buehlmann adrian at cadifra.com
Thu Jun 19 13:41:36 CDT 2008


On 19.06.2008 11:49, Adrian Buehlmann wrote:
> It seems we *can* create long path files on Windows XP using
> \\?\.. and the ...W functions of win32file.

With this updated quick hack below, which tries to work around getting the size of a file
(sorry, I'm a Python learner; didn't have a cleaner quick solution; suggestions welcome):

diff --git a/mercurial/revlog.py b/mercurial/revlog.py
--- a/mercurial/revlog.py
+++ b/mercurial/revlog.py
@@ -356,7 +356,11 @@

     def parseindex(self, fp, inline):
         try:
-            size = util.fstat(fp).st_size
+            if hasattr(fp, "size") and callable(getattr(fp, "size")):
+               # assuming util_win32.posixfile_nt
+               size = fp.size()
+            else:
+               size = util.fstat(fp).st_size
         except AttributeError:
             size = 0

diff --git a/mercurial/util_win32.py b/mercurial/util_win32.py
--- a/mercurial/util_win32.py
+++ b/mercurial/util_win32.py
@@ -268,7 +268,8 @@

     def __init__(self, name, mode='rb'):
         self.closed = False
-        self.name = name
+        # use long file names. Must be absolute and use backslash path sep only
+        self.name = '\\\\?\\' + name.replace('/','\\')
         self.mode = mode
         access = 0
         if 'r' in mode or '+' in mode:
@@ -282,7 +283,9 @@
         else:
             creation = win32file.CREATE_ALWAYS
         try:
-            self.handle = win32file.CreateFile(name,
+            print "creating file: %s" % self.name
+            # use ..W function in order to get \\?\.. long paths through
+            self.handle = win32file.CreateFileW(self.name,
                                                access,
                                                win32file.FILE_SHARE_READ |
                                                win32file.FILE_SHARE_WRITE |
@@ -292,7 +295,7 @@
                                                win32file.FILE_ATTRIBUTE_NORMAL,
                                                0)
         except pywintypes.error, err:
-            raise WinIOError(err, name)
+            raise WinIOError(err, self.name)

     def __iter__(self):
         for line in self.read().splitlines(True):
@@ -359,6 +362,9 @@
         except pywintypes.error, err:
             raise WinIOError(err)

+    def size(self):
+        return win32file.GetFileSize(self.handle)
+
 getuser_fallback = win32api.GetUserName

 def set_signal_handler_win32():


I can do a verify of that horrible repo on Windows XP !


> hgt verify
--- running hg from W:\hg-longpath
creating file: \\?\W:\tmp\long1\.hg\requires
creating file: \\?\W:\tmp\long1\.hg\store\00changelog.i
checking changesets
creating file: \\?\W:\tmp\long1\.hg\store\00changelog.d
creating file: \\?\W:\tmp\long1\.hg\store\00changelog.i
checking manifests
creating file: \\?\W:\tmp\long1\.hg\store\00manifest.i
creating file: \\?\W:\tmp\long1\.hg\store\00manifest.d
creating file: \\?\W:\tmp\long1\.hg\store\00manifest.i
crosschecking files in changesets and manifests
checking files
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___o_v_e_r___t_h_e___l_a_z_y___d_o_g__
_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___a___s_e_c_o_n_d___t_i_m_e___t_h_e___q_u_i_c_k___b_r_o_w_n.txt.i
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___o_v_e_r___t_h_e___l_a_z_y___d_o_g__
_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___a___s_e_c_o_n_d___t_i_m_e___t_h_e___q_u_i_c_k___b_r_o_w_n.txt.d
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___o_v_e_r___t_h_e___l_a_z_y___d_o_g__
_t_h_e___q_u_i_c_k___b_r_o_w_n___f_o_x___j_u_m_p_s___a___s_e_c_o_n_d___t_i_m_e___t_h_e___q_u_i_c_k___b_r_o_w_n.txt.i
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\a.txt.i
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\a.txt.d
creating file: \\?\W:\tmp\long1\.hg\store\data\_t_h_i_s___i_s___a_n___i_n_c_r_e_d_i_b_l_y___l_o_n_g___n_a_m_e___w_h_i_c_h___m_e_r_c_u_r_i_a_l___r_e_p_o_s_i
_t_o_r_i_e_s___w_i_l_l___h_a_v_e___a___h_a_r_d___t_i_m_e___w_i_t_h\a.txt.i
2 files, 2 changesets, 2 total revisions




More information about the Mercurial-devel mailing list