Re: [PATCH 1/2] libselinux: add support for pcre2

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 09/07/2016 02:25 PM, Stephen Smalley wrote:
> On 09/07/2016 04:08 AM, Janis Danisevskis wrote:
>> From: Janis Danisevskis <jdanis@xxxxxxxxxx>
>>
>> This patch moves all pcre1/2 dependencies into the new files regex.h
>> and regex.c implementing the common denominator of features needed
>> by libselinux. The compiler flag -DUSE_PCRE2 toggles between the
>> used implementations.
>>
>> As of this patch libselinux supports either pcre or pcre2 but not
>> both at the same time. The persistently stored file contexts
>> information differs. This means libselinux can only load file
>> context files generated by sefcontext_compile build with the
>> same pcre variant.
>>
>> Also, for pcre2 the persistent format is architecture dependant.
>> Stored precompiled regular expressions can only be used on the
>> same architecture they were generated on. If pcre2 is used and
>> sefcontext_compile shall generate portable output, it and libselinux
>> must be compiled with -DNO_PERSISTENTLY_STORED_PATTERNS, at the
>> cost of having to recompile the regular expressions at load time.
>>
>> Signed-off-by: Janis Danisevskis <jdanis@xxxxxxxxxx>
>> ---
>>  libselinux/Makefile                   |  13 ++
>>  libselinux/src/Makefile               |   4 +-
>>  libselinux/src/label_file.c           |  91 ++------
>>  libselinux/src/label_file.h           |  54 ++---
>>  libselinux/src/regex.c                | 405 ++++++++++++++++++++++++++++++++++
>>  libselinux/src/regex.h                | 168 ++++++++++++++
>>  libselinux/utils/Makefile             |   4 +-
>>  libselinux/utils/sefcontext_compile.c |  53 +----
>>  8 files changed, 637 insertions(+), 155 deletions(-)
>>  create mode 100644 libselinux/src/regex.c
>>  create mode 100644 libselinux/src/regex.h
>>
> 
>> diff --git a/libselinux/src/label_file.c b/libselinux/src/label_file.c
>> index c89bb35..6698624 100644
>> --- a/libselinux/src/label_file.c
>> +++ b/libselinux/src/label_file.c
>> @@ -278,7 +280,11 @@ static int load_mmap(struct selabel_handle *rec, const char *path,
>>  
>>  		spec = &data->spec_arr[data->nspec];
>>  		spec->from_mmap = 1;
>> +#if defined USE_PCRE2 && defined NO_PERSISTENTLY_STORED_PATTERNS
>> +		spec->regcomp = 0;
>> +#else
>>  		spec->regcomp = 1;
>> +#endif
> 
> If we still need this, maybe regex_load_mmap() should take
> &spec->regcomp as an argument and set it internally so that we don't
> need to litter this file with #ifdefs?
> 
>> diff --git a/libselinux/src/label_file.h b/libselinux/src/label_file.h
>> index 6d1e890..a2e30e5 100644
>> --- a/libselinux/src/label_file.h
>> +++ b/libselinux/src/label_file.h
>> @@ -394,7 +371,8 @@ static inline int process_line(struct selabel_handle *rec,
>>  	struct saved_data *data = (struct saved_data *)rec->data;
>>  	struct spec *spec_arr;
>>  	unsigned int nspec = data->nspec;
>> -	const char *errbuf = NULL;
>> +	char const *errbuf;
>> +	struct regex_error_data error_data;
>>  
>>  	items = read_spec_entries(line_buf, &errbuf, 3, &regex, &type, &context);
>>  	if (items < 0) {
>> @@ -454,7 +432,7 @@ static inline int process_line(struct selabel_handle *rec,
>>  	data->nspec++;
>>  
>>  	if (rec->validating &&
>> -			    compile_regex(data, &spec_arr[nspec], &errbuf)) {
>> +			    compile_regex(data, &spec_arr[nspec], &error_data)) {
>>  		COMPAT_LOG(SELINUX_ERROR,
>>  			   "%s:  line %u has invalid regex %s:  %s\n",
>>  			   path, lineno, regex,
> 
> On the next line (omitted from the diff) we pass errbuf if set as the
> error string.  But your error is hidden in error_data.  Looks like we
> need to use regex_format_error() here?
> 
>> diff --git a/libselinux/src/regex.c b/libselinux/src/regex.c
>> new file mode 100644
>> index 0000000..6b92b04
>> --- /dev/null
>> +++ b/libselinux/src/regex.c
>> +int regex_load_mmap(struct mmap_area * mmap_area, struct regex_data ** regex) {
>> +	int rc;
>> +	size_t entry_len;
>> +#ifndef USE_PCRE2
>> +	size_t info_len;
>> +#endif
>> +
>> +	rc = next_entry(&entry_len, mmap_area, sizeof(uint32_t));
> 
> This and similar statements are the cause of your uninitialised variable
> use warnings.  entry_len needs to be a uint32_t here.  size_t is 64 bits
> on 64-bit architectures.  Same for info_len.

Oops, sorry, never mind about info_len.  That one stays as size_t.

> 
>> +struct regex_data * regex_data_create(void) {
>> +	struct regex_data * dummy = (struct regex_data*) malloc(
>> +			sizeof(struct regex_data));
>> +	if (dummy) {
>> +		memset(dummy, 0, sizeof(struct regex_data));
>> +	}
>> +	return dummy;
>> +}
>> +
>> +void regex_data_free(struct regex_data * regex) {
>> +	if (regex) {
>> +#ifdef USE_PCRE2
>> +		if (regex->regex) {
>> +			pcre2_code_free(regex->regex);
>> +		}
>> +		if (regex->match_data) {
>> +			pcre2_match_data_free(regex->match_data);
>> +		}
>> +#else
>> +		if (regex->regex)
>> +			pcre_free(regex->regex);
>> +		if (regex->extra_owned && regex->sd) {
>> +			pcre_free_study(regex->sd);
>> +		}
>> +#endif
>> +		free(regex);
>> +	}
>> +}
> 
> The reason you are leaking memory is that regex_data_free() is only ever
> called if !spec->from_mmap.  The old code in closef() to free the
> compiled regexes was only necessary when the regexes were compiled at
> runtime, but you have introduced a memory allocation for regex_data even
> for the mmap'd file that needs to be freed.
> 
> 

_______________________________________________
Selinux mailing list
Selinux@xxxxxxxxxxxxx
To unsubscribe, send email to Selinux-leave@xxxxxxxxxxxxx.
To get help, send an email containing "help" to Selinux-request@xxxxxxxxxxxxx.



[Index of Archives]     [Selinux Refpolicy]     [Linux SGX]     [Fedora Users]     [Fedora Desktop]     [Yosemite Photos]     [Yosemite Camping]     [Yosemite Campsites]     [KDE Users]     [Gnome Users]

  Powered by Linux