The branch, v4-15-stable has been updated via bd9db127ff4 VERSION: Disable GIT_SNAPSHOT for the 4.15.4 release. via 6700eeac21d WHATSNEW: Add release notes for Samba 4.15.4. via 2a59fd316f7 auth/ntlmssp: make sure we return INVALID_PARAMETER for NTLMv2_RESPONSE parsing errors via af3c6b570f2 s4:torture/smb2: add smb2.session.ntlmssp_bug14932 test via a4bf80d8203 libcli/auth: let NTLMv2_RESPONSE_verify_netlogon_creds ignore invalid netapp requests via aa9889230fe libcli/auth: let NTLMv2_RESPONSE_verify_netlogon_creds ignore BUFFER_TOO_SMALL via 3ffd53f9e76 s4:torture/rpc: add test for invalid av_pair content in LogonSamLogonEx via 058c8a5278d auth/credentials: cli_credentials_set_ntlm_response() pass session_keys via 6d158512e8d s3:smbd: handle --build-options without parsing smb.conf via a4281c9ea7f s3:libsmb: fix signing regression SMBC_server_internal() via a9c32e69546 s4:selftest: run libsmbclient.noanon_list against maptoguest via 025749c3773 s4:torture/libsmbclient: add libsmbclient.noanon_list test via dfabc5da386 selftest/Samba3: enable SMB1 for maptoguest via 5a2227d704c s3: smbd: Add missing pop_sec_ctx() in error code path of close_directory() via 6c28c948a49 ctdb-protocol: Allow rfc5952 "[2001:db8::1]:80" ipv6 notation via 671dee2bd7d s3:smbd: Fix dereferencing null pointer "fsp" via 680f68a072c s3:modules: VFS CAP symlinkat always fails via 76e7fdb70c6 s3:modules: Fix the horrible vfs_crossrename module via 4a6e8bc5e29 s3: smbclient: In do_host_query(), if we need SMB1, ensure we select NT1 as the client max protocol" before continuing. via 4907ecaaf4e s3: selftest: Add two tests that show we try and send an SMB1 request over an SMB2 connection to list servers if "-mSMB3" is selected. via a43ad2777e3 s3: includes: Make the comments describing itime consistent. Always use "invented" time. via 85941fe0cd1 s3: lib: In create_clock_itime(), use timespec_current() -> clock_gettime(CLOCK_REALTIME..). via b48e5c61aaf s3: smbd: Create and use a common function for generating a fileid - create_clock_itime(). via 263aeea95d8 lib: util: Add a function nt_time_to_unix_timespec_raw(). via 032df88d61d tests: Add 2 tests for unique fileid's with top bit set (generated from itime) for files and directories. via 96cd0ab567e VERSION: Bump version up to Samba 4.15.4... from 0c85a0adaa5 VERSION: Disable GIT_SNAPSHOT for the 4.15.3 release.
https://git.samba.org/?p=samba.git;a=shortlog;h=v4-15-stable - Log ----------------------------------------------------------------- ----------------------------------------------------------------------- Summary of changes: VERSION | 2 +- WHATSNEW.txt | 68 ++++++- auth/credentials/credentials.h | 6 +- auth/credentials/credentials_internal.h | 2 + auth/credentials/credentials_ntlm.c | 65 ++++++- auth/ntlmssp/ntlmssp_server.c | 8 + ctdb/protocol/protocol_util.c | 13 ++ lib/util/time.c | 30 +++ lib/util/time.h | 2 + libcli/auth/smbencrypt.c | 89 ++++++++- selftest/knownfail.d/smb1-tests | 10 +- selftest/target/Samba3.pm | 1 + source3/client/client.c | 1 + source3/include/includes.h | 4 +- source3/include/proto.h | 1 + source3/lib/system.c | 52 +++++ source3/libsmb/libsmb_server.c | 2 +- source3/modules/vfs_cap.c | 2 +- source3/modules/vfs_crossrename.c | 2 +- .../script/tests/test_smbclient_list_servers.sh | 45 +++++ source3/selftest/tests.py | 20 ++ source3/smbd/close.c | 2 + source3/smbd/dosmode.c | 3 +- source3/smbd/open.c | 6 +- source3/smbd/server.c | 9 +- source4/selftest/tests.py | 17 ++ source4/torture/libsmbclient/libsmbclient.c | 50 +++++ source4/torture/rpc/schannel.c | 209 +++++++++++++++++++++ source4/torture/smb2/create.c | 205 ++++++++++++++++++++ source4/torture/smb2/session.c | 51 +++++ source4/torture/smb2/smb2.c | 1 + 31 files changed, 938 insertions(+), 40 deletions(-) create mode 100755 source3/script/tests/test_smbclient_list_servers.sh Changeset truncated at 500 lines: diff --git a/VERSION b/VERSION index a1b01a89332..ad5995baf95 100644 --- a/VERSION +++ b/VERSION @@ -25,7 +25,7 @@ ######################################################## SAMBA_VERSION_MAJOR=4 SAMBA_VERSION_MINOR=15 -SAMBA_VERSION_RELEASE=3 +SAMBA_VERSION_RELEASE=4 ######################################################## # If a official release has a serious bug # diff --git a/WHATSNEW.txt b/WHATSNEW.txt index 05eb72be9e0..9cb58de2a61 100644 --- a/WHATSNEW.txt +++ b/WHATSNEW.txt @@ -1,3 +1,68 @@ + ============================== + Release Notes for Samba 4.15.4 + January 19, 2022 + ============================== + + +This is the latest stable release of the Samba 4.15 release series. + + +Changes since 4.15.3 +-------------------- + +o Jeremy Allison <j...@samba.org> + * BUG 14928: Duplicate SMB file_ids leading to Windows client cache + poisoning. + * BUG 14939: smbclient -L doesn't set "client max protocol" to NT1 before + calling the "Reconnecting with SMB1 for workgroup listing" path. + * BUG 14944: Missing pop_sec_ctx() in error path inside close_directory(). + +o Pavel Filipenský <pfili...@redhat.com> + * BUG 14940: Cross device copy of the crossrename module always fails. + * BUG 14941: symlinkat function from VFS cap module always fails with an + error. + * BUG 14942: Fix possible fsp pointer deference. + +o Volker Lendecke <v...@samba.org> + * BUG 14934: kill_tcp_connections does not work. + +o Stefan Metzmacher <me...@samba.org> + * BUG 14932: Failed to parse NTLMv2_RESPONSE length 95 - Buffer Size Error - + NT_STATUS_BUFFER_TOO_SMALL. + * BUG 14935: Can't connect to Windows shares not requiring authentication + using KDE/Gnome. + +o Andreas Schneider <a...@samba.org> + * BUG 14945: "smbd --build-options" no longer works without an smb.conf file. + +o Jones Syue <joness...@qnap.com> + * BUG 14928: Duplicate SMB file_ids leading to Windows client cache + poisoning. + + +####################################### +Reporting bugs & Development Discussion +####################################### + +Please discuss this release on the samba-technical mailing list or by +joining the #samba-technical IRC channel on irc.libera.chat or the +#samba-technical:matrix.org matrix channel. + +If you do report problems then please try to send high quality +feedback. If you don't provide vital information to help us track down +the problem then you will probably be ignored. All bug reports should +be filed under the Samba 4.1 and newer product in the project's Bugzilla +database (https://bugzilla.samba.org/). + + +====================================================================== +== Our Code, Our Bugs, Our Responsibility. +== The Samba Team +====================================================================== + + +Release notes for older releases follow: +---------------------------------------- ============================== Release Notes for Samba 4.15.3 December 08, 2021 @@ -115,8 +180,7 @@ database (https://bugzilla.samba.org/). ====================================================================== -Release notes for older releases follow: ----------------------------------------- +---------------------------------------------------------------------- ============================== Release Notes for Samba 4.15.2 November 9, 2021 diff --git a/auth/credentials/credentials.h b/auth/credentials/credentials.h index 4057565ad34..551b1611826 100644 --- a/auth/credentials/credentials.h +++ b/auth/credentials/credentials.h @@ -230,8 +230,10 @@ bool cli_credentials_set_nt_hash(struct cli_credentials *cred, bool cli_credentials_set_old_nt_hash(struct cli_credentials *cred, const struct samr_Password *nt_hash); bool cli_credentials_set_ntlm_response(struct cli_credentials *cred, - const DATA_BLOB *lm_response, - const DATA_BLOB *nt_response, + const DATA_BLOB *lm_response, + const DATA_BLOB *lm_session_key, + const DATA_BLOB *nt_response, + const DATA_BLOB *nt_session_key, enum credentials_obtained obtained); int cli_credentials_set_keytab_name(struct cli_credentials *cred, struct loadparm_context *lp_ctx, diff --git a/auth/credentials/credentials_internal.h b/auth/credentials/credentials_internal.h index afbda1a4b48..3b1581acb11 100644 --- a/auth/credentials/credentials_internal.h +++ b/auth/credentials/credentials_internal.h @@ -70,7 +70,9 @@ struct cli_credentials { /* Allows NTLM pass-though authentication */ DATA_BLOB lm_response; + DATA_BLOB lm_session_key; DATA_BLOB nt_response; + DATA_BLOB nt_session_key; struct ccache_container *ccache; struct gssapi_creds_container *client_gss_creds; diff --git a/auth/credentials/credentials_ntlm.c b/auth/credentials/credentials_ntlm.c index 49505f64315..1c17148e647 100644 --- a/auth/credentials/credentials_ntlm.c +++ b/auth/credentials/credentials_ntlm.c @@ -69,6 +69,14 @@ _PUBLIC_ NTSTATUS cli_credentials_get_ntlm_response(struct cli_credentials *cred return NT_STATUS_NO_MEMORY; } } + if (cred->nt_session_key.length != 0) { + session_key = data_blob_dup_talloc(frame, + cred->nt_session_key); + if (session_key.data == NULL) { + TALLOC_FREE(frame); + return NT_STATUS_NO_MEMORY; + } + } if (cred->lm_response.length != 0) { lm_response = data_blob_dup_talloc(frame, cred->lm_response); @@ -77,6 +85,14 @@ _PUBLIC_ NTSTATUS cli_credentials_get_ntlm_response(struct cli_credentials *cred return NT_STATUS_NO_MEMORY; } } + if (cred->lm_session_key.length != 0) { + lm_session_key = data_blob_dup_talloc(frame, + cred->lm_session_key); + if (lm_session_key.data == NULL) { + TALLOC_FREE(frame); + return NT_STATUS_NO_MEMORY; + } + } if (cred->lm_response.data == NULL) { *flags = *flags & ~CLI_CRED_LANMAN_AUTH; @@ -483,19 +499,54 @@ _PUBLIC_ bool cli_credentials_set_old_nt_hash(struct cli_credentials *cred, } _PUBLIC_ bool cli_credentials_set_ntlm_response(struct cli_credentials *cred, - const DATA_BLOB *lm_response, - const DATA_BLOB *nt_response, + const DATA_BLOB *lm_response, + const DATA_BLOB *lm_session_key, + const DATA_BLOB *nt_response, + const DATA_BLOB *nt_session_key, enum credentials_obtained obtained) { if (obtained >= cred->password_obtained) { cli_credentials_set_password(cred, NULL, obtained); - if (nt_response) { - cred->nt_response = data_blob_talloc(cred, nt_response->data, nt_response->length); - talloc_steal(cred, cred->nt_response.data); + + data_blob_clear_free(&cred->lm_response); + data_blob_clear_free(&cred->lm_session_key); + data_blob_clear_free(&cred->nt_response); + data_blob_clear_free(&cred->nt_session_key); + + if (lm_response != NULL && lm_response->length != 0) { + cred->lm_response = data_blob_talloc(cred, + lm_response->data, + lm_response->length); + if (cred->lm_response.data == NULL) { + return false; + } } - if (nt_response) { - cred->lm_response = data_blob_talloc(cred, lm_response->data, lm_response->length); + if (lm_session_key != NULL && lm_session_key->length != 0) { + cred->lm_session_key = data_blob_talloc(cred, + lm_session_key->data, + lm_session_key->length); + if (cred->lm_session_key.data == NULL) { + return false; + } } + + if (nt_response != NULL && nt_response->length != 0) { + cred->nt_response = data_blob_talloc(cred, + nt_response->data, + nt_response->length); + if (cred->nt_response.data == NULL) { + return false; + } + } + if (nt_session_key != NULL && nt_session_key->length != 0) { + cred->nt_session_key = data_blob_talloc(cred, + nt_session_key->data, + nt_session_key->length); + if (cred->nt_session_key.data == NULL) { + return false; + } + } + return true; } diff --git a/auth/ntlmssp/ntlmssp_server.c b/auth/ntlmssp/ntlmssp_server.c index 939aa0ef4aa..ce78af1d32d 100644 --- a/auth/ntlmssp/ntlmssp_server.c +++ b/auth/ntlmssp/ntlmssp_server.c @@ -532,6 +532,14 @@ static NTSTATUS ntlmssp_server_preauth(struct gensec_security *gensec_security, (ndr_pull_flags_fn_t)ndr_pull_NTLMv2_RESPONSE); if (!NDR_ERR_CODE_IS_SUCCESS(err)) { nt_status = ndr_map_error2ntstatus(err); + if (NT_STATUS_EQUAL(nt_status, NT_STATUS_BUFFER_TOO_SMALL)) { + /* + * Note that invalid blobs should result in + * INVALID_PARAMETER, as demonstrated by + * smb2.session.ntlmssp_bug14932 + */ + nt_status = NT_STATUS_INVALID_PARAMETER; + } DEBUG(1,("%s: failed to parse NTLMv2_RESPONSE of length %zu for " "user=[%s] domain=[%s] workstation=[%s] - %s %s\n", __func__, ntlmssp_state->nt_resp.length, diff --git a/ctdb/protocol/protocol_util.c b/ctdb/protocol/protocol_util.c index 2d0a6f33038..3eea95a274e 100644 --- a/ctdb/protocol/protocol_util.c +++ b/ctdb/protocol/protocol_util.c @@ -240,6 +240,19 @@ static int ip_from_string(const char *str, ctdb_sock_addr *addr) uint8_t ipv4_mapped_prefix[12] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xff, 0xff }; + size_t len = strlen(str); + char s[64]; + + len = strlcpy(s, str, sizeof(s)); + if (len >= sizeof(s)) { + return EINVAL; + } + + if ((len >= 2) && (s[0] == '[') && (s[len-1] == ']')) { + s[len-1] = '\0'; + str = s+1; + p = strrchr(str, ':'); + } ret = ipv6_from_string(str, &addr->ip6); if (ret != 0) { diff --git a/lib/util/time.c b/lib/util/time.c index cec91c14791..5839e80a15b 100644 --- a/lib/util/time.c +++ b/lib/util/time.c @@ -867,6 +867,36 @@ _PUBLIC_ int get_time_zone(time_t t) return tm_diff(&tm_utc,tm); } +/* + * Raw convert an NTTIME to a unix timespec. + */ + +struct timespec nt_time_to_unix_timespec_raw( + NTTIME nt) +{ + int64_t d; + struct timespec ret; + + d = (int64_t)nt; + /* d is now in 100ns units, since jan 1st 1601". + Save off the ns fraction. */ + + /* + * Take the last seven decimal digits and multiply by 100. + * to convert from 100ns units to 1ns units. + */ + ret.tv_nsec = (long) ((d % (1000 * 1000 * 10)) * 100); + + /* Convert to seconds */ + d /= 1000*1000*10; + + /* Now adjust by 369 years to make the secs since 1970 */ + d -= TIME_FIXUP_CONSTANT_INT; + + ret.tv_sec = (time_t)d; + return ret; +} + struct timespec nt_time_to_unix_timespec(NTTIME nt) { int64_t d; diff --git a/lib/util/time.h b/lib/util/time.h index 72347b39b99..bdb67de5431 100644 --- a/lib/util/time.h +++ b/lib/util/time.h @@ -343,6 +343,8 @@ bool nt_time_equal(NTTIME *t1, NTTIME *t2); void interpret_dos_date(uint32_t date,int *year,int *month,int *day,int *hour,int *minute,int *second); +struct timespec nt_time_to_unix_timespec_raw(NTTIME nt); + struct timespec nt_time_to_unix_timespec(NTTIME nt); time_t convert_timespec_to_time_t(struct timespec ts); diff --git a/libcli/auth/smbencrypt.c b/libcli/auth/smbencrypt.c index 468374699f7..fe20fe4e2a3 100644 --- a/libcli/auth/smbencrypt.c +++ b/libcli/auth/smbencrypt.c @@ -675,6 +675,69 @@ NTSTATUS NTLMv2_RESPONSE_verify_netlogon_creds(const char *account_name, return NT_STATUS_OK; } + if (response.length == 95) { + /* + * ndr_pull_NTLMv2_RESPONSE() fails on this strange blob, + * because the AvPairs content is not valid + * as AvLen of the first pair is 33032 (0x8108). + * + * I saw a single machine sending the following 3 times + * in a row, but I'm not sure if everything is static. + * + * Note this is NTLMv2_CLIENT_CHALLENGE only, not + * the full NTLMv2_RESPONSE (which has Response of 16 bytes + * before the NTLMv2_CLIENT_CHALLENGE). + * + * Note this code only prevents + * ndr_pull_error(Buffer Size Error): Pull bytes 39016 + * debug message for a known case, the actual + * bug is also handled below in a generic way to + * map NT_STATUS_BUFFER_TOO_SMALL to NT_STATUS_OK. + * + * See https://bugzilla.samba.org/show_bug.cgi?id=14932 + */ + static const char *netapp_magic = + "\x01\x01\x00\x00\x00\x00\x00\x00" + "\x3f\x3f\x3f\x3f\x3f\x3f\x3f\x3f" + "\xb8\x82\x3a\xf1\xb3\xdd\x08\x15" + "\x00\x00\x00\x00\x11\xa2\x08\x81" + "\x50\x38\x22\x78\x2b\x94\x47\xfe" + "\x54\x94\x7b\xff\x17\x27\x5a\xb4" + "\xf4\x18\xba\xdc\x2c\x38\xfd\x5b" + "\xfb\x0e\xc1\x85\x1e\xcc\x92\xbb" + "\x9b\xb1\xc4\xd5\x53\x14\xff\x8c" + "\x76\x49\xf5\x45\x90\x19\xa2"; + /* + * First we check the initial bytes + * and the 0x3F timestamp. + */ + cmp = memcmp(response.data + 16, + netapp_magic, + 16); + if (cmp == 0) { + /* + * Then check everything after the + * client challenge + */ + cmp = memcmp(response.data + 40, + netapp_magic + 24, + response.length - 40); + if (cmp == 0) { + DBG_DEBUG("Invalid NETAPP NTLMv2_RESPONSE " + "for user[%s\\%s] against " + "SEC_CHAN(%u)[%s/%s] " + "in workgroup[%s]\n", + account_domain, + account_name, + creds->secure_channel_type, + creds->computer_name, + creds->account_name, + workgroup); + return NT_STATUS_OK; + } + } + } + frame = talloc_stackframe(); err = ndr_pull_struct_blob(&response, frame, &v2_resp, @@ -682,11 +745,27 @@ NTSTATUS NTLMv2_RESPONSE_verify_netlogon_creds(const char *account_name, if (!NDR_ERR_CODE_IS_SUCCESS(err)) { NTSTATUS status; status = ndr_map_error2ntstatus(err); - DEBUG(2,("Failed to parse NTLMv2_RESPONSE " - "length %u - %s - %s\n", - (unsigned)response.length, - ndr_map_error2string(err), - nt_errstr(status))); + if (NT_STATUS_EQUAL(status, NT_STATUS_BUFFER_TOO_SMALL)) { + /* + * We are supposed to ignore invalid buffers, + * see https://bugzilla.samba.org/show_bug.cgi?id=14932 + */ + status = NT_STATUS_OK; + } + DEBUG(2,("%s: Failed to parse NTLMv2_RESPONSE length=%u " + "for user[%s\\%s] against SEC_CHAN(%u)[%s/%s] " + "in workgroup[%s] - %s %s %s\n", + __func__, + (unsigned)response.length, + account_domain, + account_name, + creds->secure_channel_type, + creds->computer_name, + creds->account_name, + workgroup, + ndr_map_error2string(err), + NT_STATUS_IS_OK(status) ? "(ignoring) =>" : "=>", + nt_errstr(status))); dump_data(2, response.data, response.length); TALLOC_FREE(frame); return status; diff --git a/selftest/knownfail.d/smb1-tests b/selftest/knownfail.d/smb1-tests index 4790ef0f46c..28a74863c6a 100644 --- a/selftest/knownfail.d/smb1-tests +++ b/selftest/knownfail.d/smb1-tests @@ -1,9 +1,7 @@ -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient anonymous.badpassword.NT1NEW.guest\(maptoguest\) -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient baduser.badpassword.NT1NEW.guest\(maptoguest\) -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient username.password.NT1OLD\((ad_member|fl2000dc|maptoguest|nt4_member)\) -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient username.password.NT1NEW\((ad_member|fl2000dc|maptoguest|nt4_member)\) -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient anonymous.nopassword.NT1OLD\((ad_member|fl2000dc|maptoguest|nt4_member)\) -^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient anonymous.nopassword.NT1NEW\((ad_member|fl2000dc|maptoguest|nt4_member)\) +^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient username.password.NT1OLD\((ad_member|fl2000dc|nt4_member)\) +^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient username.password.NT1NEW\((ad_member|fl2000dc|nt4_member)\) +^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient anonymous.nopassword.NT1OLD\((ad_member|fl2000dc|nt4_member)\) +^samba3.blackbox.smbclient_ntlm.plain.*NT1.smbclient anonymous.nopassword.NT1NEW\((ad_member|fl2000dc|nt4_member)\) ^samba3.blackbox.smbclient_s3.NT1.(plain|sign).member_creds.smbclient -L.*\((ad_member|nt4_member)\) ^samba3.blackbox.smbclient_s3.NT1.(plain|sign).member_creds.smbclient -L LOCALADMEMBER -I.*\((ad_member|nt4_member)\) ^samba3.blackbox.smbclient_s3.NT1.(plain|sign).member_creds.noninteractive smbclient does not prompt\((ad_member|nt4_member)\) diff --git a/selftest/target/Samba3.pm b/selftest/target/Samba3.pm index d1ac5c16c26..84903b87d3e 100755 --- a/selftest/target/Samba3.pm +++ b/selftest/target/Samba3.pm @@ -2091,6 +2091,7 @@ sub setup_maptoguest my $options = " map to guest = bad user ntlm auth = yes +server min protocol = LANMAN1 [force_user_error_inject] path = $share_dir diff --git a/source3/client/client.c b/source3/client/client.c index 98425048f4b..a8e11044b39 100644 --- a/source3/client/client.c +++ b/source3/client/client.c @@ -6169,6 +6169,7 @@ static int do_host_query(const char *query_host) cli_shutdown(cli); d_printf("Reconnecting with SMB1 for workgroup listing.\n"); + lp_set_cmdline("client max protocol", "NT1"); status = cli_cm_open(talloc_tos(), NULL, query_host, "IPC$", diff --git a/source3/include/includes.h b/source3/include/includes.h index 6fc2ee25d95..c3d3d351e41 100644 --- a/source3/include/includes.h +++ b/source3/include/includes.h @@ -205,10 +205,10 @@ struct stat_ex { struct timespec st_ex_ctime; struct timespec st_ex_btime; /* birthtime */ /* - * Immutable original birth time aka instantiation time. Set when a file + * Immutable original birth time aka invented time. Set when a file * is created, never changes thereafter. May not be set by the client. */ - struct timespec st_ex_itime; /* instantiation time */ + struct timespec st_ex_itime; /* invented time */ blksize_t st_ex_blksize; blkcnt_t st_ex_blocks; diff --git a/source3/include/proto.h b/source3/include/proto.h index a96c2c8d110..20d026f83b3 100644 --- a/source3/include/proto.h +++ b/source3/include/proto.h @@ -175,6 +175,7 @@ void update_stat_ex_create_time(struct stat_ex *dst, struct timespec create_time void update_stat_ex_file_id(struct stat_ex *dst, uint64_t file_id); void update_stat_ex_from_saved_stat(struct stat_ex *dst, const struct stat_ex *src); +void create_clock_itime(struct stat_ex *dst); int sys_stat(const char *fname, SMB_STRUCT_STAT *sbuf, bool fake_dir_create_times); int sys_fstat(int fd, SMB_STRUCT_STAT *sbuf, diff --git a/source3/lib/system.c b/source3/lib/system.c index a14fc51ca63..83dc79101c9 100644 -- Samba Shared Repository