lib/linear_ranges.c

Source file repositories/reference/linux-study-clean/lib/linear_ranges.c

File Facts

System
Linux kernel
Corpus path
lib/linear_ranges.c
Extension
.c
Size
9658 bytes
Lines
313
Domain
Kernel Services
Bucket
lib
Inferred role
Kernel Services: exported/initcall integration point
Status
integration implementation candidate

Why This File Exists

Shared kernel service surface used by multiple subsystems, including helpers, cryptography, virtualization support, and async I/O infrastructure.

Dependency Surface

Detected Declarations

Annotated Snippet

// SPDX-License-Identifier: GPL-2.0
/*
 * helpers to map values in a linear range to range index
 *
 * Original idea borrowed from regulator framework
 *
 * It might be useful if we could support also inversely proportional ranges?
 * Copyright 2020 ROHM Semiconductors
 */

#include <linux/errno.h>
#include <linux/export.h>
#include <linux/kernel.h>
#include <linux/linear_range.h>
#include <linux/module.h>

/**
 * linear_range_values_in_range - return the amount of values in a range
 * @r:		pointer to linear range where values are counted
 *
 * Compute the amount of values in range pointed by @r. Note, values can
 * be all equal - range with selectors 0,...,2 with step 0 still contains
 * 3 values even though they are all equal.
 *
 * Return: the amount of values in range pointed by @r
 */
unsigned int linear_range_values_in_range(const struct linear_range *r)
{
	if (!r)
		return 0;
	return r->max_sel - r->min_sel + 1;
}
EXPORT_SYMBOL_GPL(linear_range_values_in_range);

/**
 * linear_range_values_in_range_array - return the amount of values in ranges
 * @r:		pointer to array of linear ranges where values are counted
 * @ranges:	amount of ranges we include in computation.
 *
 * Compute the amount of values in ranges pointed by @r. Note, values can
 * be all equal - range with selectors 0,...,2 with step 0 still contains
 * 3 values even though they are all equal.
 *
 * Return: the amount of values in first @ranges ranges pointed by @r
 */
unsigned int linear_range_values_in_range_array(const struct linear_range *r,
						int ranges)
{
	int i, values_in_range = 0;

	for (i = 0; i < ranges; i++) {
		int values;

		values = linear_range_values_in_range(&r[i]);
		if (!values)
			return values;

		values_in_range += values;
	}
	return values_in_range;
}
EXPORT_SYMBOL_GPL(linear_range_values_in_range_array);

/**
 * linear_range_get_max_value - return the largest value in a range
 * @r:		pointer to linear range where value is looked from
 *
 * Return: the largest value in the given range
 */
unsigned int linear_range_get_max_value(const struct linear_range *r)
{
	return r->min + (r->max_sel - r->min_sel) * r->step;
}
EXPORT_SYMBOL_GPL(linear_range_get_max_value);

/**
 * linear_range_get_value - fetch a value from given range
 * @r:		pointer to linear range where value is looked from
 * @selector:	selector for which the value is searched
 * @val:	address where found value is updated
 *
 * Search given ranges for value which matches given selector.
 *
 * Return: 0 on success, -EINVAL given selector is not found from any of the
 * ranges.
 */
int linear_range_get_value(const struct linear_range *r, unsigned int selector,
			   unsigned int *val)
{
	if (r->min_sel > selector || r->max_sel < selector)

Annotation

Implementation Notes