@@ -135,7 +135,8 @@ static int git_mailmap_parse_single(
135135 * real_name = name_a ;
136136
137137 if (two_emails ) {
138- * real_email = email_a ;
138+ if (email_a .len > 0 )
139+ * real_email = email_a ;
139140 * replace_email = email_b ;
140141
141142 if (name_b .len > 0 )
@@ -158,6 +159,9 @@ int git_mailmap_parse(
158159 git_mailmap_entry * entry = NULL ;
159160 int error = 0 ;
160161
162+ if (memchr (data , '\0' , size ) != NULL )
163+ return -1 ; /* data may not contain '\0's */
164+
161165 * mailmap = git__calloc (1 , sizeof (git_mailmap ));
162166 if (!* mailmap )
163167 return -1 ;
@@ -194,6 +198,7 @@ int git_mailmap_parse(
194198 error = -1 ;
195199 goto cleanup ;
196200 }
201+ entry -> version = GIT_MAILMAP_ENTRY_VERSION ;
197202
198203 buf = (char * )(entry + 1 );
199204 entry -> real_name = range_copyz (& buf , NULL , real_name );
@@ -209,9 +214,8 @@ int git_mailmap_parse(
209214 }
210215
211216cleanup :
212- if (entry )
213- git__free (entry );
214- if (error < 0 && * mailmap ) {
217+ git__free (entry );
218+ if (error < 0 )
215219 git_mailmap_free (* mailmap );
216220 * mailmap = NULL ;
217221 }
@@ -220,22 +224,29 @@ int git_mailmap_parse(
220224
221225void git_mailmap_free (git_mailmap * mailmap )
222226{
227+ if (!mailmap )
228+ return ;
229+
223230 git_vector_free_deep (& mailmap -> entries );
224231 git__free (mailmap );
225232}
226233
227234void git_mailmap_resolve (
228235 const char * * name_out ,
229236 const char * * email_out ,
230- git_mailmap * mailmap ,
237+ const git_mailmap * mailmap ,
231238 const char * name ,
232239 const char * email )
233240{
234- git_mailmap_entry * entry = NULL ;
241+ const git_mailmap_entry * entry = NULL ;
242+ assert (name && email );
235243
236244 * name_out = name ;
237245 * email_out = email ;
238246
247+ if (!mailmap )
248+ return ;
249+
239250 entry = git_mailmap_entry_lookup (mailmap , name , email );
240251 if (entry ) {
241252 if (entry -> real_name )
@@ -245,14 +256,17 @@ void git_mailmap_resolve(
245256 }
246257}
247258
248- git_mailmap_entry * git_mailmap_entry_lookup (
249- git_mailmap * mailmap ,
259+ const git_mailmap_entry * git_mailmap_entry_lookup (
260+ const git_mailmap * mailmap ,
250261 const char * name ,
251262 const char * email )
252263{
253264 size_t i ;
254265 git_mailmap_entry * entry ;
255- assert (mailmap && name && email );
266+ assert (name && email );
267+
268+ if (!mailmap )
269+ return NULL ;
256270
257271 git_vector_foreach (& mailmap -> entries , i , entry ) {
258272 if (!git__strcmp (email , entry -> replace_email ) &&
@@ -264,26 +278,42 @@ git_mailmap_entry *git_mailmap_entry_lookup(
264278 return NULL ;
265279}
266280
267- git_mailmap_entry * git_mailmap_entry_byindex (git_mailmap * mailmap , size_t idx )
281+ const git_mailmap_entry * git_mailmap_entry_byindex (
282+ const git_mailmap * mailmap , size_t idx )
268283{
269- return git_vector_get (& mailmap -> entries , idx );
284+ if (mailmap )
285+ return git_vector_get (& mailmap -> entries , idx );
286+ return NULL ;
270287}
271288
272- size_t git_mailmap_entry_count (git_mailmap * mailmap )
289+ size_t git_mailmap_entry_count (const git_mailmap * mailmap )
273290{
274- return git_vector_length (& mailmap -> entries );
291+ if (mailmap )
292+ return git_vector_length (& mailmap -> entries );
293+ return 0 ;
275294}
276295
277- int git_mailmap_from_tree (
296+ static int git_mailmap_from_bare_repo (
278297 git_mailmap * * mailmap ,
279- const git_object * treeish )
298+ git_repository * repo )
280299{
300+ git_reference * head = NULL ;
301+ git_object * tree = NULL ;
281302 git_blob * blob = NULL ;
282303 const char * content = NULL ;
283304 git_off_t size = 0 ;
284305 int error ;
285306
286- * mailmap = NULL ;
307+ assert (git_repository_is_bare (repo ));
308+
309+ /* In bare repositories, fall back to reading from HEAD's tree */
310+ error = git_repository_head (& head , repo );
311+ if (error < 0 )
312+ goto cleanup ;
313+
314+ error = git_reference_peel (& tree , head , GIT_OBJ_TREE );
315+ if (error < 0 )
316+ goto cleanup ;
287317
288318 error = git_object_lookup_bypath (
289319 (git_object * * ) & blob ,
@@ -297,28 +327,55 @@ int git_mailmap_from_tree(
297327 size = git_blob_rawsize (blob );
298328
299329 error = git_mailmap_parse (mailmap , content , size );
330+ if (error < 0 )
331+ goto cleanup ;
300332
301333cleanup :
302- if (blob != NULL )
303- git_blob_free (blob );
334+ git_reference_free (head );
335+ git_object_free (tree );
336+ git_blob_free (blob );
337+
304338 return error ;
305339}
306340
307- int git_mailmap_from_repo (git_mailmap * * mailmap , git_repository * repo )
341+ static int git_mailmap_from_workdir_repo (
342+ git_mailmap * * mailmap ,
343+ git_repository * repo )
308344{
309- git_object * head = NULL ;
345+ git_buf path = GIT_BUF_INIT ;
346+ git_buf data = GIT_BUF_INIT ;
310347 int error ;
311348
312- * mailmap = NULL ;
349+ assert (! git_repository_is_bare ( repo )) ;
313350
314- error = git_revparse_single (& head , repo , "HEAD" );
351+ /* In non-bare repositories, .mailmap should be read from the workdir */
352+ error = git_buf_joinpath (& path , git_repository_workdir (repo ), ".mailmap" );
315353 if (error < 0 )
316354 goto cleanup ;
317355
318- error = git_mailmap_from_tree (mailmap , head );
356+ error = git_futils_readbuffer (& data , git_buf_cstr (& path ));
357+ if (error < 0 )
358+ goto cleanup ;
359+
360+ error = git_mailmap_parse (mailmap , data .ptr , data .size );
361+ if (error < 0 )
362+ goto cleanup ;
319363
320364cleanup :
321- if (head )
322- git_object_free (head );
365+ git_buf_free (& path );
366+ git_buf_free (& data );
367+
323368 return error ;
324369}
370+
371+ int git_mailmap_from_repo (git_mailmap * * mailmap , git_repository * repo )
372+ {
373+ assert (mailmap && repo );
374+
375+ * mailmap = NULL ;
376+
377+ if (git_repository_is_bare (repo ))
378+ return git_mailmap_from_bare_repo (mailmap , repo );
379+ else
380+ return git_mailmap_from_workdir_repo (mailmap , repo );
381+ }
0 commit comments