Quellcodebibliothek Statistik Leitseite products/sources/formale Sprachen/C/Linux/sound/soc/fsl/   (Open Source Betriebssystem Version 6.17.9©)  Datei vom 24.10.2025 mit Größe 5 kB image not shown  

Quelle  fsl_utils.c   Sprache: C

 
// SPDX-License-Identifier: GPL-2.0
//
// Freescale ALSA SoC Machine driver utility
//
// Author: Timur Tabi <timur@freescale.com>
//
// Copyright 2010 Freescale Semiconductor, Inc.

#include <linux/clk.h>
#include <linux/clk-provider.h>
#include <linux/module.h>
#include <linux/of_address.h>
#include <sound/soc.h>

#include "fsl_utils.h"

/**
 * fsl_asoc_get_dma_channel - determine the dma channel for a SSI node
 *
 * @ssi_np: pointer to the SSI device tree node
 * @name: name of the phandle pointing to the dma channel
 * @dai: ASoC DAI link pointer to be filled with platform_name
 * @dma_channel_id: dma channel id to be returned
 * @dma_id: dma id to be returned
 *
 * This function determines the dma and channel id for given SSI node.  It
 * also discovers the platform_name for the ASoC DAI link.
 */

int fsl_asoc_get_dma_channel(struct device_node *ssi_np,
        const char *name,
        struct snd_soc_dai_link *dai,
        unsigned int *dma_channel_id,
        unsigned int *dma_id)
{
 struct resource res;
 struct device_node *dma_channel_np, *dma_np;
 const __be32 *iprop;
 int ret;

 dma_channel_np = of_parse_phandle(ssi_np, name, 0);
 if (!dma_channel_np)
  return -EINVAL;

 if (!of_device_is_compatible(dma_channel_np, "fsl,ssi-dma-channel")) {
  of_node_put(dma_channel_np);
  return -EINVAL;
 }

 /* Determine the dev_name for the device_node.  This code mimics the
 * behavior of of_device_make_bus_id(). We need this because ASoC uses
 * the dev_name() of the device to match the platform (DMA) device with
 * the CPU (SSI) device.  It's all ugly and hackish, but it works (for
 * now).
 *
 * dai->platform name should already point to an allocated buffer.
 */

 ret = of_address_to_resource(dma_channel_np, 0, &res);
 if (ret) {
  of_node_put(dma_channel_np);
  return ret;
 }
 snprintf((char *)dai->platforms->name, DAI_NAME_SIZE, "%llx.%pOFn",
   (unsigned long long) res.start, dma_channel_np);

 iprop = of_get_property(dma_channel_np, "cell-index", NULL);
 if (!iprop) {
  of_node_put(dma_channel_np);
  return -EINVAL;
 }
 *dma_channel_id = be32_to_cpup(iprop);

 dma_np = of_get_parent(dma_channel_np);
 iprop = of_get_property(dma_np, "cell-index", NULL);
 if (!iprop) {
  of_node_put(dma_np);
  of_node_put(dma_channel_np);
  return -EINVAL;
 }
 *dma_id = be32_to_cpup(iprop);

 of_node_put(dma_np);
 of_node_put(dma_channel_np);

 return 0;
}
EXPORT_SYMBOL(fsl_asoc_get_dma_channel);

/**
 * fsl_asoc_get_pll_clocks - get two PLL clock source
 *
 * @dev: device pointer
 * @pll8k_clk: PLL clock pointer for 8kHz
 * @pll11k_clk: PLL clock pointer for 11kHz
 *
 * This function get two PLL clock source
 */

void fsl_asoc_get_pll_clocks(struct device *dev, struct clk **pll8k_clk,
        struct clk **pll11k_clk)
{
 *pll8k_clk = devm_clk_get(dev, "pll8k");
 if (IS_ERR(*pll8k_clk))
  *pll8k_clk = NULL;

 *pll11k_clk = devm_clk_get(dev, "pll11k");
 if (IS_ERR(*pll11k_clk))
  *pll11k_clk = NULL;
}
EXPORT_SYMBOL(fsl_asoc_get_pll_clocks);

/**
 * fsl_asoc_reparent_pll_clocks - set clock parent if necessary
 *
 * @dev: device pointer
 * @clk: root clock pointer
 * @pll8k_clk: PLL clock pointer for 8kHz
 * @pll11k_clk: PLL clock pointer for 11kHz
 * @ratio: target requency for root clock
 *
 * This function set root clock parent according to the target ratio
 */

void fsl_asoc_reparent_pll_clocks(struct device *dev, struct clk *clk,
      struct clk *pll8k_clk,
      struct clk *pll11k_clk, u64 ratio)
{
 struct clk *p, *pll = NULL, *npll = NULL;
 bool reparent = false;
 int ret;

 if (!clk || !pll8k_clk || !pll11k_clk)
  return;

 p = clk;
 while (p && pll8k_clk && pll11k_clk) {
  struct clk *pp = clk_get_parent(p);

  if (clk_is_match(pp, pll8k_clk) ||
      clk_is_match(pp, pll11k_clk)) {
   pll = pp;
   break;
  }
  p = pp;
 }

 npll = (do_div(ratio, 8000) ? pll11k_clk : pll8k_clk);
 reparent = (pll && !clk_is_match(pll, npll));

 if (reparent) {
  ret = clk_set_parent(p, npll);
  if (ret < 0)
   dev_warn(dev, "failed to set parent:%d\n", ret);
 }
}
EXPORT_SYMBOL(fsl_asoc_reparent_pll_clocks);

/**
 * fsl_asoc_constrain_rates - constrain rates according to clocks
 *
 * @target_constr: target constraint
 * @original_constr: original constraint
 * @pll8k_clk: PLL clock pointer for 8kHz
 * @pll11k_clk: PLL clock pointer for 11kHz
 * @ext_clk: External clock pointer
 * @target_rates: target rates array
 *
 * This function constrain rates according to clocks
 */

void fsl_asoc_constrain_rates(struct snd_pcm_hw_constraint_list *target_constr,
         const struct snd_pcm_hw_constraint_list *original_constr,
         struct clk *pll8k_clk, struct clk *pll11k_clk,
         struct clk *ext_clk, int *target_rates)
{
 int i, j, k = 0;
 u64 clk_rate[3];

 *target_constr = *original_constr;
 if (pll8k_clk || pll11k_clk || ext_clk) {
  target_constr->list = target_rates;
  target_constr->count = 0;
  for (i = 0; i < original_constr->count; i++) {
   clk_rate[0] = clk_get_rate(pll8k_clk);
   clk_rate[1] = clk_get_rate(pll11k_clk);
   clk_rate[2] = clk_get_rate(ext_clk);
   for (j = 0; j < 3; j++) {
    if (clk_rate[j] != 0 &&
        do_div(clk_rate[j], original_constr->list[i]) == 0) {
     target_rates[k++] = original_constr->list[i];
     target_constr->count++;
     break;
    }
   }
  }

  /* protection for if there is no proper rate found*/
  if (!target_constr->count)
   *target_constr = *original_constr;
 }
}
EXPORT_SYMBOL(fsl_asoc_constrain_rates);

MODULE_AUTHOR("Timur Tabi ");
MODULE_DESCRIPTION("Freescale ASoC utility code");
MODULE_LICENSE("GPL v2");

Messung V0.5
C=94 H=91 G=92

¤ Dauer der Verarbeitung: 0.15 Sekunden  (vorverarbeitet)  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.