@@ -1499,6 +1499,7 @@ struct ondisk_cache_entry_extended {
1499
1499
};
1500
1500
1501
1501
/* These are only used for v3 or lower */
1502
+ #define align_padding_size (size , len ) ((size + (len) + 8) & ~7) - (size + len)
1502
1503
#define align_flex_name (STRUCT ,len ) ((offsetof(struct STRUCT,name) + (len) + 8) & ~7)
1503
1504
#define ondisk_cache_entry_size (len ) align_flex_name(ondisk_cache_entry,len)
1504
1505
#define ondisk_cache_entry_extended_size (len ) align_flex_name(ondisk_cache_entry_extended,len)
@@ -2032,7 +2033,7 @@ static void ce_smudge_racily_clean_entry(struct cache_entry *ce)
2032
2033
}
2033
2034
2034
2035
/* Copy miscellaneous fields but not the name */
2035
- static char * copy_cache_entry_to_ondisk (struct ondisk_cache_entry * ondisk ,
2036
+ static void copy_cache_entry_to_ondisk (struct ondisk_cache_entry * ondisk ,
2036
2037
struct cache_entry * ce )
2037
2038
{
2038
2039
short flags ;
@@ -2056,32 +2057,35 @@ static char *copy_cache_entry_to_ondisk(struct ondisk_cache_entry *ondisk,
2056
2057
struct ondisk_cache_entry_extended * ondisk2 ;
2057
2058
ondisk2 = (struct ondisk_cache_entry_extended * )ondisk ;
2058
2059
ondisk2 -> flags2 = htons ((ce -> ce_flags & CE_EXTENDED_FLAGS ) >> 16 );
2059
- return ondisk2 -> name ;
2060
- }
2061
- else {
2062
- return ondisk -> name ;
2063
2060
}
2064
2061
}
2065
2062
2066
2063
static int ce_write_entry (git_SHA_CTX * c , int fd , struct cache_entry * ce ,
2067
- struct strbuf * previous_name )
2064
+ struct strbuf * previous_name , struct ondisk_cache_entry * ondisk )
2068
2065
{
2069
2066
int size ;
2070
- struct ondisk_cache_entry * ondisk ;
2071
2067
int saved_namelen = saved_namelen ; /* compiler workaround */
2072
- char * name ;
2073
2068
int result ;
2069
+ static unsigned char padding [8 ] = { 0x00 };
2074
2070
2075
2071
if (ce -> ce_flags & CE_STRIP_NAME ) {
2076
2072
saved_namelen = ce_namelen (ce );
2077
2073
ce -> ce_namelen = 0 ;
2078
2074
}
2079
2075
2076
+ if (ce -> ce_flags & CE_EXTENDED )
2077
+ size = offsetof(struct ondisk_cache_entry_extended , name );
2078
+ else
2079
+ size = offsetof(struct ondisk_cache_entry , name );
2080
+
2080
2081
if (!previous_name ) {
2081
- size = ondisk_ce_size (ce );
2082
- ondisk = xcalloc (1 , size );
2083
- name = copy_cache_entry_to_ondisk (ondisk , ce );
2084
- memcpy (name , ce -> name , ce_namelen (ce ));
2082
+ int len = ce_namelen (ce );
2083
+ copy_cache_entry_to_ondisk (ondisk , ce );
2084
+ result = ce_write (c , fd , ondisk , size );
2085
+ if (!result )
2086
+ result = ce_write (c , fd , ce -> name , len );
2087
+ if (!result )
2088
+ result = ce_write (c , fd , padding , align_padding_size (size , len ));
2085
2089
} else {
2086
2090
int common , to_remove , prefix_size ;
2087
2091
unsigned char to_remove_vi [16 ];
@@ -2094,16 +2098,12 @@ static int ce_write_entry(git_SHA_CTX *c, int fd, struct cache_entry *ce,
2094
2098
to_remove = previous_name -> len - common ;
2095
2099
prefix_size = encode_varint (to_remove , to_remove_vi );
2096
2100
2097
- if (ce -> ce_flags & CE_EXTENDED )
2098
- size = offsetof(struct ondisk_cache_entry_extended , name );
2099
- else
2100
- size = offsetof(struct ondisk_cache_entry , name );
2101
- size += prefix_size + (ce_namelen (ce ) - common + 1 );
2102
-
2103
- ondisk = xcalloc (1 , size );
2104
- name = copy_cache_entry_to_ondisk (ondisk , ce );
2105
- memcpy (name , to_remove_vi , prefix_size );
2106
- memcpy (name + prefix_size , ce -> name + common , ce_namelen (ce ) - common );
2101
+ copy_cache_entry_to_ondisk (ondisk , ce );
2102
+ result = ce_write (c , fd , ondisk , size );
2103
+ if (!result )
2104
+ result = ce_write (c , fd , to_remove_vi , prefix_size );
2105
+ if (!result )
2106
+ result = ce_write (c , fd , ce -> name + common , ce_namelen (ce ) - common + 1 );
2107
2107
2108
2108
strbuf_splice (previous_name , common , to_remove ,
2109
2109
ce -> name + common , ce_namelen (ce ) - common );
@@ -2113,8 +2113,6 @@ static int ce_write_entry(git_SHA_CTX *c, int fd, struct cache_entry *ce,
2113
2113
ce -> ce_flags &= ~CE_STRIP_NAME ;
2114
2114
}
2115
2115
2116
- result = ce_write (c , fd , ondisk , size );
2117
- free (ondisk );
2118
2116
return result ;
2119
2117
}
2120
2118
@@ -2192,10 +2190,11 @@ static int do_write_index(struct index_state *istate, struct tempfile *tempfile,
2192
2190
int newfd = tempfile -> fd ;
2193
2191
git_SHA_CTX c ;
2194
2192
struct cache_header hdr ;
2195
- int i , err , removed , extended , hdr_version ;
2193
+ int i , err = 0 , removed , extended , hdr_version ;
2196
2194
struct cache_entry * * cache = istate -> cache ;
2197
2195
int entries = istate -> cache_nr ;
2198
2196
struct stat st ;
2197
+ struct ondisk_cache_entry_extended ondisk ;
2199
2198
struct strbuf previous_name_buf = STRBUF_INIT , * previous_name ;
2200
2199
int drop_cache_tree = 0 ;
2201
2200
@@ -2232,6 +2231,7 @@ static int do_write_index(struct index_state *istate, struct tempfile *tempfile,
2232
2231
return -1 ;
2233
2232
2234
2233
previous_name = (hdr_version == 4 ) ? & previous_name_buf : NULL ;
2234
+
2235
2235
for (i = 0 ; i < entries ; i ++ ) {
2236
2236
struct cache_entry * ce = cache [i ];
2237
2237
if (ce -> ce_flags & CE_REMOVE )
@@ -2247,15 +2247,21 @@ static int do_write_index(struct index_state *istate, struct tempfile *tempfile,
2247
2247
if (allow )
2248
2248
warning (msg , ce -> name );
2249
2249
else
2250
- return error (msg , ce -> name );
2250
+ err = error (msg , ce -> name );
2251
2251
2252
2252
drop_cache_tree = 1 ;
2253
2253
}
2254
- if (ce_write_entry (& c , newfd , ce , previous_name ) < 0 )
2255
- return -1 ;
2254
+ if (ce_write_entry (& c , newfd , ce , previous_name , (struct ondisk_cache_entry * )& ondisk ) < 0 )
2255
+ err = -1 ;
2256
+
2257
+ if (err )
2258
+ break ;
2256
2259
}
2257
2260
strbuf_release (& previous_name_buf );
2258
2261
2262
+ if (err )
2263
+ return err ;
2264
+
2259
2265
/* Write extension data here */
2260
2266
if (!strip_extensions && istate -> split_index ) {
2261
2267
struct strbuf sb = STRBUF_INIT ;
0 commit comments