Lines 63-68
struct dlz_bind9_data {
|
Link Here
|
---|
|
63 |
struct smb_krb5_context *smb_krb5_ctx; |
63 |
struct smb_krb5_context *smb_krb5_ctx; |
64 |
struct auth4_context *auth_context; |
64 |
struct auth4_context *auth_context; |
65 |
struct auth_session_info *session_info; |
65 |
struct auth_session_info *session_info; |
|
|
66 |
bool is_system_session; |
66 |
char *update_name; |
67 |
char *update_name; |
67 |
|
68 |
|
68 |
/* helper functions from the dlz_dlopen driver */ |
69 |
/* helper functions from the dlz_dlopen driver */ |
Lines 736-741
_PUBLIC_ void dlz_destroy(void *dbdata)
|
Link Here
|
---|
|
736 |
dlz_bind9_state_ref_count--; |
737 |
dlz_bind9_state_ref_count--; |
737 |
if (dlz_bind9_state_ref_count == 0) { |
738 |
if (dlz_bind9_state_ref_count == 0) { |
738 |
talloc_unlink(state, state->samdb); |
739 |
talloc_unlink(state, state->samdb); |
|
|
740 |
if (state->is_system_session) { |
741 |
state->session_info = NULL; |
742 |
} |
739 |
talloc_free(state); |
743 |
talloc_free(state); |
740 |
dlz_bind9_state = NULL; |
744 |
dlz_bind9_state = NULL; |
741 |
} |
745 |
} |
Lines 1269-1274
static bool b9_is_tombstoned(struct ldb_result *res) {
|
Link Here
|
---|
|
1269 |
} |
1273 |
} |
1270 |
|
1274 |
|
1271 |
/* |
1275 |
/* |
|
|
1276 |
* If `name` is a computer account (ends in $) and the records's field matches |
1277 |
* the account name (without the $), the account owns the record. |
1278 |
*/ |
1279 |
static bool b9_account_owns_record(const char *name, struct ldb_result *record) { |
1280 |
char *dc = NULL; |
1281 |
size_t len = strlen(name); |
1282 |
|
1283 |
struct ldb_message_element *el = ldb_msg_find_element(record->msgs[0], "dc"); |
1284 |
if (el != NULL && el->num_values > 0) { |
1285 |
dc = (char *) el->values[0].data; |
1286 |
} |
1287 |
|
1288 |
if (dc != NULL && len > 0 && name[len - 1] == '$') { |
1289 |
return strncmp(name, dc, len - 1) == 0; |
1290 |
} |
1291 |
return false; |
1292 |
} |
1293 |
|
1294 |
/* |
1272 |
authorize a zone update |
1295 |
authorize a zone update |
1273 |
*/ |
1296 |
*/ |
1274 |
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const char *tcpaddr, |
1297 |
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const char *tcpaddr, |
Lines 1285-1300
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const
|
Link Here
|
---|
|
1285 |
NTSTATUS nt_status; |
1308 |
NTSTATUS nt_status; |
1286 |
struct gensec_security *gensec_ctx; |
1309 |
struct gensec_security *gensec_ctx; |
1287 |
struct auth_session_info *session_info; |
1310 |
struct auth_session_info *session_info; |
|
|
1311 |
bool is_system_session = false; |
1288 |
struct ldb_dn *dn; |
1312 |
struct ldb_dn *dn; |
1289 |
isc_result_t result; |
1313 |
isc_result_t result; |
1290 |
struct ldb_result *res; |
1314 |
struct ldb_result *res; |
1291 |
const char * attrs[] = { "dNSTombstoned", NULL }; |
1315 |
const char * attrs[] = { "dNSTombstoned", "dc", NULL }; |
1292 |
uint32_t access_mask; |
1316 |
uint32_t access_mask; |
1293 |
bool is_tombstoned = false; |
1317 |
bool is_tombstoned = false; |
|
|
1318 |
bool owns_record = false; |
1294 |
|
1319 |
|
1295 |
/* Remove cached credentials, if any */ |
1320 |
/* Remove cached credentials, if any */ |
1296 |
if (state->session_info) { |
1321 |
if (state->session_info) { |
1297 |
talloc_free(state->session_info); |
1322 |
if (!state->is_system_session) { |
|
|
1323 |
talloc_free(state->session_info); |
1324 |
} |
1325 |
state->is_system_session = false; |
1298 |
state->session_info = NULL; |
1326 |
state->session_info = NULL; |
1299 |
} |
1327 |
} |
1300 |
if (state->update_name) { |
1328 |
if (state->update_name) { |
Lines 1381-1386
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const
|
Link Here
|
---|
|
1381 |
} else if (ldb_ret == LDB_SUCCESS) { |
1409 |
} else if (ldb_ret == LDB_SUCCESS) { |
1382 |
access_mask = SEC_STD_REQUIRED | SEC_ADS_SELF_WRITE; |
1410 |
access_mask = SEC_STD_REQUIRED | SEC_ADS_SELF_WRITE; |
1383 |
is_tombstoned = b9_is_tombstoned(res); |
1411 |
is_tombstoned = b9_is_tombstoned(res); |
|
|
1412 |
owns_record = b9_account_owns_record(session_info->info->account_name, res); |
1384 |
talloc_free(res); |
1413 |
talloc_free(res); |
1385 |
} else { |
1414 |
} else { |
1386 |
talloc_free(tmp_ctx); |
1415 |
talloc_free(tmp_ctx); |
Lines 1412-1417
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const
|
Link Here
|
---|
|
1412 |
session_info->security_token, |
1441 |
session_info->security_token, |
1413 |
access_mask, NULL); |
1442 |
access_mask, NULL); |
1414 |
} |
1443 |
} |
|
|
1444 |
/* Univention Specific: If a machine tries to access a forward/zone |
1445 |
* without the proper access-rights, but the account of the requesting |
1446 |
* machine matches the `dc` attribute of the record, a modification is |
1447 |
* allowed and the privileges for this operation are escalated to |
1448 |
* `SYSTEM`. |
1449 |
*/ |
1450 |
if (ldb_ret == LDB_ERR_INSUFFICIENT_ACCESS_RIGHTS && owns_record) { |
1451 |
session_info = system_session(state->lp); |
1452 |
is_system_session = true; |
1453 |
ldb_ret = LDB_SUCCESS; |
1454 |
} |
1415 |
if (ldb_ret != LDB_SUCCESS) { |
1455 |
if (ldb_ret != LDB_SUCCESS) { |
1416 |
state->log(ISC_LOG_INFO, |
1456 |
state->log(ISC_LOG_INFO, |
1417 |
"samba_dlz: disallowing update of signer=%s name=%s type=%s error=%s", |
1457 |
"samba_dlz: disallowing update of signer=%s name=%s type=%s error=%s", |
Lines 1427-1433
_PUBLIC_ isc_boolean_t dlz_ssumatch(const char *signer, const char *name, const
|
Link Here
|
---|
|
1427 |
talloc_free(tmp_ctx); |
1467 |
talloc_free(tmp_ctx); |
1428 |
return ISC_FALSE; |
1468 |
return ISC_FALSE; |
1429 |
} |
1469 |
} |
1430 |
state->session_info = talloc_steal(state, session_info); |
1470 |
state->is_system_session = is_system_session; |
|
|
1471 |
if (is_system_session) { |
1472 |
state->session_info = session_info; |
1473 |
} else { |
1474 |
state->session_info = talloc_steal(state, session_info); |
1475 |
} |
1431 |
|
1476 |
|
1432 |
state->log(ISC_LOG_INFO, "samba_dlz: allowing update of signer=%s name=%s tcpaddr=%s type=%s key=%s", |
1477 |
state->log(ISC_LOG_INFO, "samba_dlz: allowing update of signer=%s name=%s tcpaddr=%s type=%s key=%s", |
1433 |
signer, name, tcpaddr, type, key); |
1478 |
signer, name, tcpaddr, type, key); |
1434 |
- |
|
|