blob: 0b43e6f20fbba368b52a32beb36bf6e8e95391c5 [file] [log] [blame]
/*
* This file is part of the flashprog project.
*
* Copyright (C) 2026 Nico Huber <nico.h@gmx.de>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include <stdlib.h>
#define flashprog_chip flashchip /* For now, we use direct pointers */
#include "libflashprog.h" /* to the internal struct flashchip. */
#include "flash.h"
#include "flashchips.h"
/**
* @defgroup flashprog-chips Chip Enumeration
* @{
*/
/* Magic pointer that represents our built in database. */
#define FLASHCHIPS_DB (struct flashprog_chips *)(uintptr_t)-1
static bool chip_from_db(const struct flashprog_chip *chip) {
return flashchips <= chip && chip < flashchips + flashchips_size;
}
/**
* @brief Enumerate the internal chips database.
*
* @param[out] chips Points to a struct flashprog_chips pointer that gets
* set if the enumeration is successful. *chips has to be
* freed by the caller with @ref flashprog_chips_release.
* @return 0 on success
*/
int flashprog_chips_all(struct flashprog_chips **chips) {
*chips = FLASHCHIPS_DB;
return 0;
}
/**
* @brief Count the chips in an enumeration.
*
* @return The number of chips.
*/
unsigned int flashprog_chips_count(const struct flashprog_chips *chips)
{
unsigned int count = 0;
const struct flashprog_chip *chip;
for (chip = flashprog_chip_first(chips); chip; chip = flashprog_chip_next(chip))
++count;
return count;
}
/**
* @brief Free a set of enumerated chips.
*
* This also invalidates all references that were acquired via
* @ref flashprog_chip_first or @ref flashprog_chip_next from
* the given set.
*
* @param chips Chip enumeration to free.
*/
void flashprog_chips_release(struct flashprog_chips *chips)
{
if (chips == FLASHCHIPS_DB)
return;
free(chips);
}
/**
* @brief Starts an iteration over a given set of enumerated chips.
*
* The referenced chip structure will stay valid until either the iteration
* is advanced (@ref flashprog_chip_next) or the provided chips enumeration
* is released. Note, each call may allocated additional resources that are
* only freed by walking the iteration to its end, or releasing the entire
* chips set.
*
* @param chips A set of enumerated chips.
* @return A pointer to the structure of the first chip or NULL if the set is empty.
*/
const struct flashprog_chip *flashprog_chip_first(const struct flashprog_chips *chips)
{
if (chips == FLASHCHIPS_DB)
return flashchips;
return NULL;
}
/**
* @brief Iterates to the next chip structure in a set of enumerated chips.
*
* The referenced chip structure will stay valid until either the iteration
* is advanced further or the original chips enumeration is released (cf.
* @ref flashprog_chip_first).
*
* @param chip The previous chip in the enumeration. The referenced
* structure will be invalidated by the call.
* @return A pointer to the structure of the next chip or NULL if there is none.
*/
const struct flashprog_chip *flashprog_chip_next(const struct flashprog_chip *chip)
{
if (chip_from_db(chip)) {
for (++chip; chip->name; ++chip) {
if (chip->id.manufacture == PROGMANUF_ID)
continue;
if (chip->id.manufacture == GENERIC_MANUF_ID)
continue;
if (chip->id.model == GENERIC_DEVICE_ID)
continue;
return chip;
}
return NULL;
}
return NULL;
}
/** @} */ /* end flashprog-chips */
/**
* @defgroup flashprog-chip Chip Information
* @{
*/
/**
* @brief Get the vendor string of a given chip structure.
*
* @param chip reference to query.
* @return Vendor string.
*/
const char *flashprog_chip_vendor(const struct flashprog_chip *chip) {
return chip->vendor;
}
/**
* @brief Get the name string of a given chip structure.
*
* @param chip reference to query.
* @return Name string.
*/
const char *flashprog_chip_name(const struct flashprog_chip *chip) {
return chip->name;
}
/**
* @brief Get the size of a given chip in bytes.
*
* @param chip reference to query.
* @return Size in bytes.
*/
size_t flashprog_chip_size(const struct flashprog_chip *chip) {
return chip->total_size * KiB;
}
/**
* @brief Get a bit mask of the supported bus types.
*
* @param chip reference to query.
* @return bit mask of supported bus types.
*/
enum flashprog_bus_type flashprog_chip_buses(const struct flashprog_chip *chip) {
return chip->bustype;
}
/**
* @brief Get a string that lists the supported bus types.
*
* The resulting string needs to be freed with free().
*
* @param chip reference to query.
* @return comma-separated string of supported bus types.
*/
char *flashprog_chip_bus_names(const struct flashprog_chip *chip) {
return flashbuses_to_text(chip->bustype);
}
/**
* @brief Get the supported operating voltage range.
*
* @param chip reference to query.
* @return supported operating voltage range.
*/
struct flashprog_voltage_range flashprog_chip_voltage_range(const struct flashprog_chip *chip)
{
return (struct flashprog_voltage_range) {
.min = chip->voltage.min / 1000.f,
.max = chip->voltage.max / 1000.f,
};
}
/**
* @brief Get the test status of a chip's standard features.
*
* @param chip reference to query.
* @return struct with the test status of the chip's standard features.
*/
struct flashprog_test_status flashprog_chip_test_status(const struct flashprog_chip *chip) {
return chip->tested;
}
/** @} */ /* end flashprog-chip */