OSDN Git Service

made wingit.dll delay load so that PATH can be inited with git/bin dir before dll...
[tortoisegit/TortoiseGitJp.git] / src / Git / GitStatus.h
1 #pragma once\r
2 \r
3 #ifdef _MFC_VER\r
4 //#     include "SVNPrompt.h"\r
5 #endif\r
6 #include "TGitPath.h"\r
7 \r
8 #pragma warning (push,1)\r
9 typedef std::basic_string<wchar_t> wide_string;\r
10 #ifdef UNICODE\r
11 #       define stdstring wide_string\r
12 #else\r
13 #       define stdstring std::string\r
14 #endif\r
15 #pragma warning (pop)\r
16 \r
17 #include "TGitPath.h"\r
18 #include "../../ext/wingit/wingit.h"\r
19 \r
20 typedef enum type_git_wc_status_kind\r
21 {\r
22         git_wc_status_none,\r
23         git_wc_status_unversioned,\r
24         git_wc_status_ignored,\r
25         git_wc_status_normal,\r
26         git_wc_status_external,\r
27         git_wc_status_incomplete,\r
28         git_wc_status_missing,\r
29         git_wc_status_deleted,\r
30         git_wc_status_replaced,\r
31         git_wc_status_modified,\r
32         git_wc_status_merged,\r
33         git_wc_status_added,\r
34         git_wc_status_conflicted,\r
35         git_wc_status_obstructed,\r
36 \r
37 }git_wc_status_kind;\r
38 \r
39 typedef enum\r
40 {\r
41         git_depth_empty,\r
42         git_depth_infinity,\r
43         git_depth_unknown,\r
44         git_depth_files,\r
45         git_depth_immediates,\r
46 }git_depth_t;\r
47 \r
48 \r
49 #define GIT_REV_ZERO _T("0000000000000000000000000000000000000000")\r
50 #define GIT_INVALID_REVNUM _T("")\r
51 typedef CString git_revnum_t;\r
52 typedef int git_error_t;\r
53 \r
54 typedef struct git_wc_status2_t\r
55\r
56   /** The status of the entries text. */\r
57   git_wc_status_kind text_status;\r
58 \r
59   /** The status of the entries properties. */\r
60   git_wc_status_kind prop_status;\r
61 }git_wc_status2;\r
62 \r
63 #define MAX_STATUS_STRING_LENGTH                256\r
64 \r
65 \r
66 // convert wingit.dll status to git_wc_status_kind\r
67 inline static git_wc_status_kind GitStatusFromWingit(int nStatus)\r
68 {\r
69         switch (nStatus)\r
70         {\r
71         case WGFS_Normal: return git_wc_status_normal;\r
72         case WGFS_Modified: return git_wc_status_modified;\r
73         case WGFS_Deleted: return git_wc_status_deleted;\r
74 \r
75         case WGFS_Empty: return git_wc_status_unversioned;\r
76         }\r
77 \r
78         return git_wc_status_none;\r
79 }\r
80 \r
81 // convert 20 byte sha1 hash to the git_revnum_t type\r
82 inline static git_revnum_t ConvertHashToRevnum(const BYTE *sha1)\r
83 {\r
84         if (!sha1)\r
85                 return GIT_INVALID_REVNUM;\r
86 \r
87         char s[41];\r
88         char *p = s;\r
89         for (int i=0; i<20; i++)\r
90         {\r
91 #pragma warning(push)\r
92 #pragma warning(disable: 4996)\r
93                 sprintf(p, "%02x", (UINT)*sha1);\r
94 #pragma warning(pop)\r
95                 p += 2;\r
96                 sha1++;\r
97         }\r
98 \r
99         return CString(s);\r
100 }\r
101 \r
102 \r
103 /**\r
104  * \ingroup Git\r
105  * Handles Subversion status of working copies.\r
106  */\r
107 class GitStatus\r
108 {\r
109 public:\r
110         GitStatus(bool * pbCanceled = NULL);\r
111         ~GitStatus(void);\r
112 \r
113 \r
114         /**\r
115          * Reads the Subversion status of the working copy entry. No\r
116          * recurse is done, even if the entry is a directory.\r
117          * If the status of the text and property part are different\r
118          * then the more important status is returned.\r
119          */\r
120         static git_wc_status_kind GetAllStatus(const CTGitPath& path, git_depth_t depth = git_depth_empty);\r
121 \r
122         /**\r
123          * Reads the Subversion status of the working copy entry and all its\r
124          * subitems. The resulting status is determined by using priorities for\r
125          * each status. The status with the highest priority is then returned.\r
126          * If the status of the text and property part are different then\r
127          * the more important status is returned.\r
128          */\r
129         static git_wc_status_kind GetAllStatusRecursive(const CTGitPath& path);\r
130 \r
131         /**\r
132          * Returns the status which is more "important" of the two statuses specified.\r
133          * This is used for the "recursive" status functions on folders - i.e. which status\r
134          * should be returned for a folder which has several files with different statuses\r
135          * in it.\r
136          */                                     \r
137         static git_wc_status_kind GetMoreImportant(git_wc_status_kind status1, git_wc_status_kind status2);\r
138         \r
139         /**\r
140          * Checks if a status is "important", i.e. if the status indicates that the user should know about it.\r
141          * E.g. a "normal" status is not important, but "modified" is.\r
142          * \param status the status to check\r
143          */\r
144         static BOOL IsImportant(git_wc_status_kind status) {return (GetMoreImportant(git_wc_status_added, status)==status);}\r
145 \r
146         /**\r
147          * Reads the Subversion text status of the working copy entry. No\r
148          * recurse is done, even if the entry is a directory.\r
149          * The result is stored in the public member variable status.\r
150          * Use this method if you need detailed information about a file/folder, not just the raw status (like "normal", "modified").\r
151          * \r
152          * \param path the pathname of the entry\r
153          * \param update true if the status should be updated with the repository. Default is false.\r
154          * \return If update is set to true the HEAD revision of the repository is returned. If update is false then -1 is returned.\r
155          * \remark If the return value is -2 then the status could not be obtained.\r
156          */\r
157         git_revnum_t GetStatus(const CTGitPath& path, bool update = false, bool noignore = false, bool noexternals = false);\r
158 \r
159         /**\r
160          * Returns a string representation of a Subversion status.\r
161          * \param status the status enum\r
162          * \param string a string representation\r
163          */\r
164         static void GetStatusString(git_wc_status_kind status, size_t buflen, TCHAR * string);\r
165         static void GetStatusString(HINSTANCE hInst, git_wc_status_kind status, TCHAR * string, int size, WORD lang);\r
166 \r
167         /**\r
168          * Returns the string representation of a depth.\r
169          */\r
170 #ifdef _MFC_VER\r
171         static CString GetDepthString(git_depth_t depth);\r
172 #endif\r
173         static void GetDepthString(HINSTANCE hInst, git_depth_t depth, TCHAR * string, int size, WORD lang);\r
174 \r
175         /**\r
176          * Returns the status of the first file of the given path. Use GetNextFileStatus() to obtain\r
177          * the status of the next file in the list.\r
178          * \param path the path of the folder from where the status list should be obtained\r
179          * \param retPath the path of the file for which the status was returned\r
180          * \param update set this to true if you want the status to be updated with the repository (needs network access)\r
181          * \param recurse true to fetch the status recursively\r
182          * \param bNoIgnore true to not fetch the ignored files\r
183          * \param bNoExternals true to not fetch the status of included Git:externals\r
184          * \return the status\r
185          */\r
186         git_wc_status2_t * GetFirstFileStatus(const CTGitPath& path, CTGitPath& retPath, bool update = false, git_depth_t depth = git_depth_infinity, bool bNoIgnore = true, bool bNoExternals = false);\r
187         unsigned int GetFileCount() const {return /*apr_hash_count(m_statushash);*/0;}\r
188         unsigned int GetVersionedCount() const;\r
189         /**\r
190          * Returns the status of the next file in the file list. If no more files are in the list then NULL is returned.\r
191          * See GetFirstFileStatus() for details.\r
192          */\r
193         git_wc_status2_t * GetNextFileStatus(CTGitPath& retPath);\r
194         /**\r
195          * Checks if a path is an external folder.\r
196          * This is necessary since Subversion returns two entries for external folders: one with the status Git_wc_status_external\r
197          * and one with the 'real' status of that folder. GetFirstFileStatus() and GetNextFileStatus() only return the 'real'\r
198          * status, so with this method it's possible to check if the status also is Git_wc_status_external.\r
199          */\r
200         bool IsExternal(const CTGitPath& path) const;\r
201         /**\r
202          * Checks if a path is in an external folder.\r
203          */\r
204         bool IsInExternal(const CTGitPath& path) const;\r
205 \r
206         /**\r
207          * Clears the memory pool.\r
208          */\r
209         void ClearPool();\r
210 \r
211         /**\r
212          * This member variable hold the status of the last call to GetStatus().\r
213          */\r
214         git_wc_status2_t *                      status;                         ///< the status result of GetStatus()\r
215 \r
216         git_revnum_t                            headrev;                        ///< the head revision fetched with GetFirstStatus()\r
217 \r
218         bool *                                          m_pbCanceled;\r
219 #ifdef _MFC_VER\r
220 friend class Git;       // So that Git can get to our m_err\r
221         /**\r
222          * Returns the last error message as a CString object.\r
223          */\r
224         CString GetLastErrorMsg() const;\r
225 \r
226         /** \r
227          * Set a list of paths which will be considered when calling GetFirstFileStatus.\r
228          * If a filter is set, then GetFirstFileStatus/GetNextFileStatus will only return items which are in the filter list\r
229          */\r
230         void SetFilter(const CTGitPathList& fileList);\r
231         void ClearFilter();\r
232 \r
233 #else\r
234         /**\r
235          * Returns the last error message as a CString object.\r
236          */\r
237         stdstring GetLastErrorMsg() const;\r
238 #endif\r
239 \r
240 \r
241 protected:\r
242 //      apr_pool_t *                            m_pool;                 ///< the memory pool\r
243 private:\r
244         typedef struct sort_item\r
245         {\r
246                 const void *key;\r
247 //              apr_ssize_t klen;\r
248                 void *value;\r
249         } sort_item;\r
250 \r
251         typedef struct hashbaton_t\r
252         {\r
253                 GitStatus*              pThis;\r
254 //              apr_hash_t *    hash;\r
255 //              apr_hash_t *    exthash;\r
256         } hash_baton_t;\r
257 \r
258 //      git_client_ctx_t *                      ctx;\r
259         git_wc_status_kind                      m_allstatus;    ///< used by GetAllStatus and GetAllStatusRecursive\r
260 //      git_error_t *                           m_err;                  ///< Subversion error baton\r
261         BOOL                                            m_err;\r
262 \r
263         git_wc_status2_t                        m_status;               // used for GetStatus\r
264 \r
265 #ifdef _MFC_VER\r
266 //      GitPrompt                                       m_prompt;\r
267 #endif\r
268 \r
269         /**\r
270          * Returns a numeric value indicating the importance of a status. \r
271          * A higher number indicates a more important status.\r
272          */\r
273         static int GetStatusRanking(git_wc_status_kind status);\r
274 \r
275         /**\r
276          * Callback function which collects the raw status from a Git_client_status() function call\r
277          */\r
278         //static git_error_t * getallstatus (void *baton, const char *path, git_wc_status2_t *status, apr_pool_t *pool);\r
279         static BOOL getallstatus(const struct wgFile_s *pFile, void *pUserData);\r
280         static BOOL getstatus(const struct wgFile_s *pFile, void *pUserData);\r
281 \r
282         /**\r
283          * Callback function which stores the raw status from a Git_client_status() function call\r
284          * in a hash table.\r
285          */\r
286 //      static git_error_t * getstatushash (void *baton, const char *path, git_wc_status2_t *status, apr_pool_t *pool);\r
287 \r
288         /**\r
289          * helper function to sort a hash to an array\r
290          */\r
291 //      static apr_array_header_t * sort_hash (apr_hash_t *ht, int (*comparison_func) (const sort_item *,\r
292 //                                                                              const sort_item *), apr_pool_t *pool);\r
293 \r
294         /**\r
295          * Callback function used by qsort() which does the comparison of two elements\r
296          */\r
297         static int __cdecl sort_compare_items_as_paths (const sort_item *a, const sort_item *b);\r
298 \r
299         //for GetFirstFileStatus and GetNextFileStatus\r
300 //      apr_hash_t *                            m_statushash;\r
301 //      apr_array_header_t *            m_statusarray;\r
302         unsigned int                            m_statushashindex;\r
303 //      apr_hash_t *                            m_externalhash;\r
304 \r
305 #pragma warning(push)\r
306 #pragma warning(disable: 4200)\r
307         struct STRINGRESOURCEIMAGE\r
308         {\r
309                 WORD nLength;\r
310                 WCHAR achString[];\r
311         };\r
312 #pragma warning(pop)    // C4200\r
313 \r
314         static int LoadStringEx(HINSTANCE hInstance, UINT uID, LPTSTR lpBuffer, int nBufferMax, WORD wLanguage);\r
315         static git_error_t* cancel(void *baton);\r
316 \r
317         // A sorted list of filenames (in Git format, in lowercase) \r
318         // when this list is set, we only pick-up files during a GetStatus which are found in this list\r
319         typedef std::vector<std::string> StdStrAVector;\r
320         StdStrAVector m_filterFileList;\r
321 };\r
322 \r
323 \r
324