@@ -212,7 +212,7 @@ int git_buf_put(git_buf *buf, const char *data, size_t len)
212212 size_t new_size ;
213213
214214 assert (data );
215-
215+
216216 GITERR_CHECK_ALLOC_ADD (& new_size , buf -> size , len );
217217 GITERR_CHECK_ALLOC_ADD (& new_size , new_size , 1 );
218218 ENSURE_SIZE (buf , new_size );
@@ -455,6 +455,36 @@ int git_buf_decode_base85(
455455 return -1 ;
456456}
457457
458+ #define HEX_DECODE (c ) ((c | 32) % 39 - 9)
459+
460+ int git_buf_decode_percent (
461+ git_buf * buf ,
462+ const char * str ,
463+ size_t str_len )
464+ {
465+ size_t str_pos , new_size ;
466+
467+ GITERR_CHECK_ALLOC_ADD (& new_size , buf -> size , str_len );
468+ GITERR_CHECK_ALLOC_ADD (& new_size , new_size , 1 );
469+ ENSURE_SIZE (buf , new_size );
470+
471+ for (str_pos = 0 ; str_pos < str_len ; buf -> size ++ , str_pos ++ ) {
472+ if (str [str_pos ] == '%' &&
473+ str_len > str_pos + 2 &&
474+ isxdigit (str [str_pos + 1 ]) &&
475+ isxdigit (str [str_pos + 2 ])) {
476+ buf -> ptr [buf -> size ] = (HEX_DECODE (str [str_pos + 1 ]) << 4 ) +
477+ HEX_DECODE (str [str_pos + 2 ]);
478+ str_pos += 2 ;
479+ } else {
480+ buf -> ptr [buf -> size ] = str [str_pos ];
481+ }
482+ }
483+
484+ buf -> ptr [buf -> size ] = '\0' ;
485+ return 0 ;
486+ }
487+
458488int git_buf_vprintf (git_buf * buf , const char * format , va_list ap )
459489{
460490 size_t expected_size , new_size ;
0 commit comments