[Aporte] Generador de Señales (DDS)

Para el barrido en frecuencia, tenia pensado que el micro cambie el prescaler cada un tiempo determinado.

Si, el tema es que tenes que crearle un menú al usuario que permita configurar la frecuencia de inicio y final del barrido y su deltaF, incluso con el programa de PC permito que sean pasos lineales, por octavas o por decadas. Hacer ese menú en el uC es un despelote y encima termina siendo recontra secuencial para el usuario (tedioso).

¿Como seria eso del barrido en duty para una onda senoidal?

El duty nada más se setea en la salida TTL.

En que la fsampling seria en vez de 8mhz, de 16mhz. A cada ciclo de reloj tengo un sample en ram, que puede ser distinto al anterior o igual, depende el prescaler. Los tiempos de propagacion de los integrados solo limitan hasta que fsampling puedo llegar, y 16 mhz *creo* que llegan (ahora que anda bien puedo probarlo). Digo *creo* porque los tiempos que calculamos mas arriba son los tipicos, pero no significa que sean necesariamente los limites. A 12mhz estoy bastante seguro que llega bien solo que no tengo un oscilador de 12mhz (antes removi el oscilador y puse un cristal en el inversor que uso para distribuir el reloj)

Pero vos no tenés control sobre el tiempo de propagación y ya mediste que te daba 125nS clavados. Vos bien me corregiste diciendo que los sumadores no usan ningún clock, por lo tanto los 100nS ya están fijos, solo queda ver que pasa con la RAM.

http://calculator-sundar.hpage.co.in/pic-pwm_88966258.html

En esta pagina, pone como frecuencia 48mhz, deja el pwm freq en blanco y pone el duty en 50%. Te va tirar la lista de todos los pwm posibles con ese micro. A medida que te vas mas arriba tenes menos "suavidad" entre saltos.

Con el AVR no puedo llegar tan lejos, porque mi cristal máximo era de 16MHz y tenía un preescaler mínimo de 256 cuentas (ba prodría reducir la resolución del duty y hacerlo de solo 100). Con 16MHz dá 60 y pico de kHz con 8MHz era que daba 30 y pico de kHz. Si lo podés hacer por el hard del uC, dale para adelante.

Los operacionales son LM318 configurados de forma tal que den el maximo slew rate (son de 50v/us y con esta configuracion trepan a 150v/us) El ancho de banda en señal pequeña es de 15mhz. No estoy seguro que puedan ir a tanto pero creo que deberian poder tirar una señal de 5vpp a 4-5mhz sin problemas. (No hice cuentas aun)

Cerca de los 5MHz todavía tenés una ganancia de 20dB (10 veces), así que podés llegar, pasando los 10MHz es casi 10dB.

Lo que te recomiendo es usar el Pspice o el LTspice (si es que tienen ese amplificador) y graficar la respuesta en frecuencia del filtro, porque estás muy cerca de los polos de lazo abierto del operacional y eso te va a correr la frecuencia de corte superior.
 
Pero vos no tenés control sobre el tiempo de propagación y ya mediste que te daba 125nS clavados. Vos bien me corregiste diciendo que los sumadores no usan ningún clock, por lo tanto los 100nS ya están fijos, solo queda ver que pasa con la RAM.

Quisiera aclararte algo que me parece que estas pasando por alto:

Si bien te dije que los sumadores no usan clock, fijate que el latch LS374 es el que determina el valor que tiene el acumulador en ESE momento (que sera sumado al valor de paso seteado por los 4094).

Los latch SI tienen clock y es en cada clock donde cambia su salida por la sumatoria. Entonces, de ahi que la velocidad de sampling es = la velocidad de reloj aplicada a los latches.

La RAM en si no tiene clock, simplemente cuando ve una direccion en la entrada, pone su dato a la salida dentro de los 25ns de aplicada la direccion.

Tenes razon en un punto y es que el conjunto sumadores + latch + ram "usa" 125ns en teoria para poner un dato a la salida, por lo tanto, estaria en teoria limitado a 8mhz. En la practica, a 16mhz funciono bien. Me queda hacer una prueba para ver si no hay "bug" o corrimiento de frecuencia como tenia con la soldadura mala, pero esta vez provocado porque algun sumador no alcance a sumar a tiempo... o un latch que no llegue a pasar bien un dato, etc. a velocidades maximas.

Por ej: Originalmente esto lo puse a 20mhz. Tenia formas de onda distorsionadas debido a que los integrados no alcanzaban a operar correctamente. Al bajar a 16mhz se corrigio pero tenia el defecto que solucionamos juntos, solamente que buscando ese defecto fue que lo baje a 8mhz. Ahora que esta eso corregido es cuestion de volver a soldar el oscilador de 16mhz y ver que pasa.
 
O sea tus sumadores son más rápidos que los 25nS originales, ya que estaban limitados por los latch. Ojo con terminar con una base de tiempo variable, deberías volver a medir la fsampling.
 
Apareció el amigo que sabe de Fpga!. :D

Si por favor, subilo, definitivamente es la mejor forma de encarar este proyecto y con que subas alguna punta tal vez se consiga que un usuario a futuro se anime y lo arme con esta tecnología.
 
A mi me fascinaria hacerlo con fpga pero de lo unico que dispongo aqui son GAL. No averigue si puedo conseguir alguna en Cordoba y no sabria como conseguir un programador. Basicamente, no se por donde empezar (altera, xilix, etc)

De momento, viendo un post tuyo cosme, me baje el Atmel Studio 6.2 ;)
 
Con respecto a empezar con FPGAs, se pueden conseguir kits de evaluacion muy buenos a costos de entre 50 y 100 dolares. Tanto Xilinx como Altera son muy buenos (hay otros), yo personalmente conozco Altera asi que si puedo ayudar con mas datos, no hay mas que preguntar.

Y ahora, el código del NCO. NCO quiere decir oscilador controlado numéricamente.

Primero las explicaciones. El codigo esta basado en una tabla seno de un cuarto de ciclo, luego usa simetria y restadores para generar los otros tres cuadrantes de la señal. Esto se hace asi porque desde el punto de vista de recursos es mucho mas "barato" una unidad de suma-resta y multiplexor, que usar una memoria interna del dispositivo cuatro veces más grande.
La lógica incluye un prescaler para generar una frecuencia intermedia.

Suponiendo que clkin = 50MHz (es lo que usa mi tarjeta de evaluación con un Cyclone III de Altera), y usando clk_divide = 780, la frecuencia generada por el prescaler es 50MHz/781 o sea aproximadamente 64kHz. Si escribo en freq_prog la cantidad 256, la frecuencia de salida sera de 64kHz. freq_prog tiene 16 bits, los ocho mas significativos son la parte entera y el resto la parte decimal.

Si con el mismo prescaler quiero obtener 1kHz, freq_prog debe ser 3.99872 (en binario, 00000011'11111111, en hexa 03FF).

En este caso la salida es de 8 bits con signo, o sea de -127 a 127. En su versión original el código está parametrizado pero lo pasé a numeros "hard coded" para mayor claridad del código en esta primera versión que posteo.


Por orden de aparición.
1 - Declaro las librerías a utilizar
2 - Declaro la entidad y sus puertos
3 - Constantes y señales
4 - Infiero los contenidos de la ROM de un cuarto de ciclo usando GENERATE en GENROM
5 - Proceso del prescaler
6 - Proceso del acumulador de fase. Noten que la fase para la tabla la tomo de la parte más significativa del acumulador (phase_in), asimismo de esa parte más significativa tomo los dos bits más significativos para el proceso de la tabla en cuatro cuadrantes (phase_sel).
7 - Genera cuatro cuadrantes de la señal senoidal aprovechando sus propiedades de simetría y signo.

Próximamente postearé resultados de un test bench.

Código:
LIBRARY ieee;
use ieee.std_logic_1164.all;
use ieee.math_real.all;
use ieee.numeric_std.ALL;

ENTITY nco IS

PORT (	
	clk 		: in std_logic;
	reset 		: in std_logic;
	
	-- NCO ports
	clk_divide	: in unsigned(11 downto 0);
	freq_prog		: in unsigned(15 downto 0);
	dout 		: out signed(7 downto 0)
);
END nco ;--
--
ARCHITECTURE rtl OF nco IS

	CONSTANT ROMSIZE : INTEGER  := 2**(8-2);
	CONSTANT ROM_W   : INTEGER  := 2**8;
	CONSTANT HALF_PI : REAL     := MATH_PI/2.0;
	CONSTANT STEP_FR : natural  := 64;
	TYPE SINTAB IS ARRAY(0 TO ROMSIZE-1) OF signed (NNCO-1 DOWNTO 0);
	
	signal SINROM: SINTAB;
	signal phase_sel   : std_logic_vector(1 downto 0);
	signal phase_accum : std_logic_vector(15 downto 0); 
	signal phase_in    : std_logic_vector(7 downto 0);
	signal freq_divide : unsigned(15 downto 0);
	signal acc_en      : std_logic;	
	
BEGIN

	-- Infer ROM sine table,
	GENROM:
	FOR idx in 0 TO ROMSIZE-1 GENERATE
		CONSTANT y: 	REAL := SIN(real(idx)*HALF_PI/real(ROMSIZE));
		CONSTANT ysc:   REAL := y*real((ROM_W-1)/2);
		CONSTANT yn: 	SIGNED (7 DOWNTO 0) := TO_SIGNED(INTEGER(ysc),8);
	BEGIN
		SINROM(idx) <= yn; 
	END GENERATE; 
	
	-- Sampling freq. generator 
	-- Divides input clk by clk_divide
    process (clk, reset) begin
        if (reset = '1') then
            acc_en		<= '0';
			freq_divide <= (others => '0');
        elsif (rising_edge(clk)) then
            acc_en 	    <= '0';
			freq_divide <= freq_divide + 1;
			if (freq_divide = clk_divide) then
				acc_en 		<= '1';
				freq_divide <= (others => '0');
			end if;	
		end if;	
	end process;
	
	-- phase accumulator
    process (clk, reset) begin
        if (reset = '1') then
            phase_accum <= (others => '0');
        elsif (rising_edge(clk)) then
			if (acc_en = '1') then
				phase_accum <= std_logic_vector(unsigned(phase_accum) + unsigned(freq_prog));
			end if;	
		end if;	
	end process;
	phase_in  <= phase_accum(15 downto 8);
	phase_sel <= phase_in(7 downto 6);

	-- phase lookup - four quadrants
    process (clk, reset) begin
        if (reset = '1') then
            dout 		<= (others => '0');
        elsif (rising_edge(clk)) then
			case (phase_sel) is
				when "00" =>
					dout <= SINROM(to_integer(unsigned(phase_in(5 downto 0))));
				when "01" =>
					dout <= SINROM(to_integer(ROMSIZE-1-unsigned(phase_in(5 downto 0))));
				when "10" =>
					dout <= -SINROM(to_integer(unsigned(phase_in(5 downto 0))));
				when "11" =>
					dout <= -SINROM(to_integer(ROMSIZE-1-unsigned(phase_in(5 downto 0))));
				when others =>	
					dout <= SINROM(to_integer(unsigned(phase_in(5 downto 0))));
			end case;		
		end if;	
	end process;
	
END;
 
Última edición:
seaarg, estuve viendo tu salida analógica. Después del primer operacional que solo lo usas como inversor, tenes dos etapas:

1- Filtro pasa bajos de 1er orden compuesto por la resistencia de 560 Ohms (R1) y el capacitor de 220pF (C1).
2- Filtro pasa bajos de 1er orden usando el segundo operacional impuesto por la resistencia de 22pF (C2) y de 1,2kOhm (R3).

La expresión matemática de todo (incluyendo el 1er operacional, simplifique las negaciones) queda así:

[LATEX]Av_{(s)}=\frac{\frac{1}{C_{1}.R_{1}}}{s+\frac{1}{C_{1}.R_{1}}}.\frac{R_{3}}{R_{2}}.\frac{\frac{1}{C_{2}.R_{3}}}{s+\frac{1}{C_{2}.R_{3}}}[/LATEX]

- La ganancia en baja frecuencia será: R3/R2.
- Vas a tener 2 polos, uno en 1,29MHz (lo impone R1 y C1) y otro en 6MHz (lo impone R3 y C2).

Esto último no está bien, porque te impone una frecuencia de corte superior inferior a 1,29MHz, es decir todo lo que venga a partir de esa frecuencia se empieza a atenuar (o mejor dicho a tener menor ganancia).

Otro problema que veo, es que no tenés un pasa altos (o un capacitor en serie) que elimine el offset de 2,5V.

Yo creo que el 1er operacional está totalmente desperdiciado y el segundo también, ya que podrías hacer un filtro de mayor orden. Pero antes que nada, vas a tener que definir bien:

- Ganancia en frecuencias bajas.
- Ancho de banda (esto incluye la necesidad de imponer una frecuencia de corte inferior => pasa altos).
- Rechazo a las frecuencias de imagen que vas a tener.
- Que tan lineal deberá ser el filtro, a menor linealidad, mayor distorsión en señales poliarmónicas.

Por cierto, ¿para qué necesitas el Atmel Studio si estás usando un PIC?
 
Ante todo, gracias por tu tiempo y tu analisis! como comente antes, en analogica hago agua :)

seaarg, estuve viendo tu salida analógica. Después del primer operacional que solo lo usas como inversor, tenes dos etapas:

Si, la idea era usarlo solamente de buffer sin amplificar ni hacer de filtro para no alterar de ningun modo la señal. Me parecio que al ser una red de resistencias, si me ponia a hacer un filtro ahi podia llegar a distorsionar o atenuar la señal original debido a la alta impedancia de la salida del R2R

1- Filtro pasa bajos de 1er orden compuesto por la resistencia de 560 Ohms (R1) y el capacitor de 220pF (C1).
2- Filtro pasa bajos de 1er orden usando el segundo operacional impuesto por la resistencia de 22pF (C2) y de 1,2kOhm (R3).

Exacto el #1, pero el #2 en realidad, si no me equivoco, era una mezcla de filtro pasabajos (capacitor) + regulacion de ganancia (relacion entre resistencia 430 ohms y 1.2k) para que me de exactamente 5vpp. Llegue a ese valor a fuerza bruta probando con el simulador ya que desconozco las formulas implicadas.


Otro problema que veo, es que no tenés un pasa altos (o un capacitor en serie) que elimine el offset de 2,5V.

No necesite eso ya que le puse un potenciometro de offset de 10k, ese que esta entre VEE y AVDD y que va al pin 3 del operacional. Con eso ajusto el offset poniendo la señal en la parte positiva enteramente o en la parte negativa y aparentemente funciona sin problemas (otra vez, llegue a esos valores experimentando)

Yo creo que el 1er operacional está totalmente desperdiciado y el segundo también, ya que podrías hacer un filtro de mayor orden. Pero antes que nada, vas a tener que definir bien:

Esto es importante me parece: ¿Vos decis que no hacia falta que el 1r operacional sea solamente buffer? Es decir, no se veria afectada la señal por la alta impedancia de la salida del DAC?

Cambiar el diseño ahora es impractico porque ya esta el PCB (es un infierno hacer este pcb de nuevo!) pero, si no es demasiada molestia, me gustaria saber si se puede mejorar esta etapa analogica cambiando valores, o haciendo modificaciones minimas que pueda hacer sobre este circuito ya ensamblado.

Por cierto, ¿para qué necesitas el Atmel Studio si estás usando un PIC?

Porque voy a intentar hacer mi proximo proyecto usando Atmel :D asi que hay que empezar a aprenderlo. Me gusto ver la diferencia de performance.
 
Exacto el #1, pero el #2 en realidad, si no me equivoco, era una mezcla de filtro pasabajos (capacitor) + regulacion de ganancia (relacion entre resistencia 430 ohms y 1.2k) para que me de exactamente 5vpp. Llegue a ese valor a fuerza bruta probando con el simulador ya que desconozco las formulas implicadas.

Claro, el 2do operacional es el que finalmente impone la ganancia, lo que yo llamo R3/R2.

No necesite eso ya que le puse un potenciometro de offset de 10k, ese que esta entre VEE y AVDD y que va al pin 3 del operacional. Con eso ajusto el offset poniendo la señal en la parte positiva enteramente o en la parte negativa y aparentemente funciona sin problemas (otra vez, llegue a esos valores experimentando)

Si, lo pensaste de forma distinta, yo preferí eliminar la componente de continua y luego agregarla o no con un pote + llave. Es cuestión de gusto.

Esto es importante me parece: ¿Vos decis que no hacia falta que el 1r operacional sea solamente buffer? Es decir, no se veria afectada la señal por la alta impedancia de la salida del DAC?

Está bien usar un buffer después de la red, pero no esa configuración que usaste, ya que presenta una impedancia de solo 5,1kOhm. Lo ideal hubiera sido usar un buffer no negador, que tiene como característica principal tener una impedancia de entrada muy alta. Lo que podés hacer, para no cambiar el PCB es aumentar el valor de esas resistencias.

Cambiar el diseño ahora es impractico porque ya esta el PCB (es un infierno hacer este pcb de nuevo!) pero, si no es demasiada molestia, me gustaria saber si se puede mejorar esta etapa analogica cambiando valores, o haciendo modificaciones minimas que pueda hacer sobre este circuito ya ensamblado.

Lo que se puede hacer es modificar los polos de esos dos filtros cambiando los valores de los capacitores/resistencia. Pero antes es necesario que definas los puntos que te puse antes:

Cosmefulanito04 dijo:
- Ganancia en frecuencias bajas.
- Ancho de banda.
- Rechazo a las frecuencias de imagen que vas a tener.
- Que tan lineal deberá ser el filtro, a menor linealidad, mayor distorsión en señales poliarmónicas.

El último punto en este caso no se aplicaría, ya que son filtros simples de 1er orden. El 1er punto ya lo definiste y queda por saber los otros dos.
 
Honestamente desconozco como definir lo que decis, ya que no se (supongo) que es el ancho de banda o frecuencia de imagen.

Ancho de banda: Asumo que implica que frecuencias quiero dejar pasar con el filtro. Si tengo un reloj de 8mhz y para representar aproximadamente una triangular necesitaria al menos 5 puntos, creo que deberia tener un ancho de banda de 1hz-1.6 mhz, o sino, una senoidal de 4 puntos: 1hz-2mhz Supongamos 2mhz si es correcto lo que interpreto.

Rechazo a las frecuencias de imagen: (cerebro tilt aca) Adivinando diria que son todas las frecuencias arriba de la maxima que quiero representar, que seria 2mhz. Google no me esta ayudando en esto porque no se como buscarlo.

Idealmente, el filtro deberia dejar pasar la señal sin atenuar hasta los 2mhz, por lo tanto, quiza la FC deba ser un poco mayor que eso, ya que no creo que este filtro sea de corte abrupto.
 
El ancho de banda es el rango de frecuencia que marcan una caída de 3dB. Como en tu caso no eliminás la comtinua, tu ancho de banda irá de DC a una frecuencia de corte superior. En esa frecuencia de corte superior, vas a tener una caída de 3dB.

Para saber el ancho de banda necesitas saber la frecuencia de sampling y la máxima frecuencia senoidal que esperás. Pero antes es necesario que entiendas lo básico del muestreo, si hacés un análisis en frecuencia de lo que hacés cuando muestreas, pasa esto:

sampling1.gif


Olvidate por un momento de las frecuencias negativas que aparecen en el gráfico que pueden confundirte un poco.

Ahí la señal X(jw) es la salida que esperás obtener (no importa la forma), cuyo ancho de banda es wm. P(jw) es la señal de muestreo (en la realidad esta señal es distinta, pero no quiero marearte), que tendrá una frecuencia de muestreo fs (o en radianes ws).

Xp(jw) sale de una operación llamada "convolución" entre X(jw) y P(jw), para resumir, esa convolución lo que hace es desplazar la señal X(jw) en c/"flechita" (delta de dirac) que tiene P(jw). Entonces si te fijás en c/ws aparece una señal X(jw) repetida (obviamente con distinta amplitud). Esa convolución se dá cuando muestras, siempre.

La idea de ese filtro pasa bajos final, es eliminar todas esas X(jw) de "más" (frecuencias imágenes) y quedarte solo con la que se encuentra entre DC y fm. Si no atenúas bien esas frecuencias de imágenes, a la salida hablando en forma temporal, aparecen y terminan deformando la señal original. Por lo tanto lo conveniente es que el nivel de atenuación de esas frecuencias imágenes sea muy alto (rechazo a la frecuencias imágenes), ¿qué tan alto? según que tan pura querés que sea la señal a la salida, en términos de senoidal, cuanto THD estás dispuesto a tolerar (además obviamente del THD que introduce el circuito en si).

Si ves la segunda Xp(jw), la que tiene solapamiento, eso sucede cuando la frecuencia máxima de la señal es mayor a fsampling/2, la famosa fórmula de nyquist, si superás fsampling/2, obtenés a la salida una deformación por aliasing.

En mi caso yo tenía una fsampling de 1,7MHz, quería llegar a una senoidal de 500kHz, por lo tanto mi frecuencia de imagen empezaba en 1,2MHz (fsampling-fseñal), yo implementé un filtro de 4to orden para tener una atenuación cercana a 24dB sobre esa frecuencia imágen. Sin embargo me encontré con otro problema que nunca terminé de solucionar, que era ese armónico de baja frecuencia que se me metía cuando la señal estaba cerca de los 500kHz.

Una forma de mejorar ese rechazo, es aumentar la fsampling o disminuir la frecuencia máxima de la señal (agregar más muestras). Aumentando la fsampling en frecuencias altas (usé un acumulador de solo 8 bits), conseguí aumentar un poco más esa fsampling, dando como resultado una mejora en la salida de los 500kHz.

Volviendo un poco a tu caso, suponiendo que lográs una fsampling de 16MHz, tu máxima frecuencia teórica será 8MHz, en forma práctica si imponés dicha frecuencia en 5MHz, la frecuencia imagen la vas a tener en 11MHz y con dos filtros de 1er orden conseguís atenuar más o menos 12dB (va a ser un poquito más).

Es decir, si querés una senoidal de 5MHz, en frecuencia vas obtener una armónica en 5MHz (la senoidal que buscás) y una armónica 12dB atenuada en 11MHz, esa 2da armónica mientras menor peso tenga, mejor se verá la senoidal de 5MHz.
 
La idea de ese filtro pasa bajos final, es eliminar todas esas X(jw) de "más" (frecuencias imágenes) y quedarte solo con la que se encuentra entre DC y fm. Si no atenúas bien esas frecuencias de imágenes, a la salida hablando en forma temporal, aparecen y terminan deformando la señal original. Por lo tanto lo conveniente es que el nivel de atenuación de esas frecuencias imágenes sea muy alto (rechazo a la frecuencias imágenes), ¿qué tan alto? según que tan pura querés que sea la señal a la salida, en términos de senoidal, cuanto THD estás dispuesto a tolerar (además obviamente del THD que introduce el circuito en si).

Muchisimas gracias por tu explicacion, los graficos me superan un poco pero tu explicacion verbal la comprendo. ¿Estas frecuencias imagen son las que, si no tuviera bien el filtro, las veria como picos fuera de la frecuencia pura esperada en el grafico de FFT?

En mi caso yo tenía una fsampling de 1,7MHz, quería llegar a una senoidal de 500kHz, por lo tanto mi frecuencia de imagen empezaba en 1,2MHz (fsampling-fseñal), yo implementé un filtro de 4to orden para tener una atenuación cercana a 24dB sobre esa frecuencia imágen. Sin embargo me encontré con otro problema que nunca terminé de solucionar, que era ese armónico de baja frecuencia que se me metía cuando la señal estaba cerca de los 500kHz.

mi fsampling=8mhz - 2mhz = 6mhz Ahi tendria que estar mi FC verdad? El armonico vos lo ves mediante la FFT o de otra forma?

Volviendo un poco a tu caso, suponiendo que lográs una fsampling de 16MHz, tu máxima frecuencia teórica será 8MHz, en forma práctica si imponés dicha frecuencia en 5MHz, la frecuencia imagen la vas a tener en 11MHz y con dos filtros de 1er orden conseguís atenuar más o menos 12dB (va a ser un poquito más).

Es decir, si querés una senoidal de 5MHz, en frecuencia vas obtener una armónica en 5MHz (la senoidal que buscás) y una armónica 12dB atenuada en 11MHz, esa 2da armónica mientras menor peso tenga, mejor se verá la senoidal de 5MHz.

A 16mhz lo probe y no llegue, los acumuladores se saltean bits. Llegaria a 12 pero lo deje en 8mhz y se me ocurre que la fmax que este bicho pueda generar manteniendo la forma seria 2mhz y el filtro deberia hacer caer los mayores dB posibles a 6mhz

¿Entendi mas o menos bien?
 
Muchisimas gracias por tu explicacion, los graficos me superan un poco pero tu explicacion verbal la comprendo. ¿Estas frecuencias imagen son las que, si no tuviera bien el filtro, las veria como picos fuera de la frecuencia pura esperada en el grafico de FFT?

Si. La FFT lo que te muestra son armónicos. Una senoidal perfecta está compuesta de un solo pico de esos.

mi fsampling=8mhz - 2mhz = 6mhz Ahi tendria que estar mi FC verdad?

No, si 2MHz es tu frecuencia de señal máxima, 6MHz será el inicio de tu frecuencia de imagen, vos tendrías que cortar a partir de 2MHz en adelante, para que en 6MHz la atenuación sea la máxima posible.

Ahora, el problema es con las señales poliarmónicas, ya que para ver más o menos la forma de onda de una señal rectangular necesitas agarrar 5 armónicos de la frecuencia fundamental, es decir si tenés una rectangular de 1MHz, para verla medianamente bien, tu filtro debería empezar a cortar recién en 5MHz (5to armónico de la fundamental de 1MHz). Por eso, mi generador está limitado a 100kHz en las señales poliarmónicas, porque la triangular se empieza a ver "fea". Por eso fogo propuso hacer un filtro variable en pasos.

El armonico vos lo ves mediante la FFT o de otra forma?

Si, fijate que en el mensaje #3, la señal violeta es el FFT. Ahí podés ver que la senoidal tiene solo un pico.

se me ocurre que la fmax que este bicho pueda generar manteniendo la forma seria 2mhz y el filtro deberia hacer caer los mayores dB posibles a 6mhz

¿Entendi mas o menos bien?

Esa sería la idea, en 6MHz tenés que conseguir la máxima atenuación posible. Con tus filtros fijados cerca de 2MHz, en 4MHz conseguís 12dB y en 6 vas a conseguir un poco más de atenuación.
 
Ok cosme, muchisimas gracias. Lo que voy a hacer es reproducir en proteus la parte de los operacionales y hacerle un analisis en frecuencia cambiando valores, o configuracion en lo posible, hasta dar con un corte como el que describis.
 
El proteus y la parte analógica no son muy compatibles. :LOL:

Como tenés varias etapas de filtros de 1er orden primero tenés que calcular la frecuencia de corte de c/filtro (que será la misma en todas las etapas), eso lo hacés así:

[LATEX]f_{corte-una-etapa}=\frac{f_{corte-total}}{\sqrt{\sqrt[n]{2}-1}}[/LATEX]

Como son 2 filtros => n=2 y si buscamos que todo el circuito presente una frecuencia de corte en 2MHz:

[LATEX]f_{corte-una-etapa}=\frac{2MHz}{\sqrt{\sqrt[2]{2}-1}}=3,1MHz[/LATEX]

Ahora tenés que usar esta fórmula para calcular el 2do filtro:

[LATEX]f_{corte-2do-filtro}=\frac{1}{2.\pi.C_{2}.R_{3}}[/LATEX]

Supongamos que le dás el valor C2=10pF => R3=5,1kOhm. Solo vas a tener que recalcular el valor de la resistencia de 430 Ohms para obtener más o menos la misma ganancia, digamos que podría valer 1,8kOhm más cerca de 2kOhm para mantener la misma ganancia.

Ahora que me doy cuenta, en el análisis del post anterior no tuve en cuenta que el 1er filtro está cargado con esa resistencia de 430Ohm y en realidad la expresión es otra. Para el primer filtro, tenés que usar esta fórmula:

[LATEX]f_{corte-1er-filtro}=\frac{R_{1}+R_{2}}{2.\pi.C_{1}.\left(R_{1}.R_{2}\right)}[/LATEX]

R2 será 1,8kOhm del 2do filtro, te queda calcular R1 y C1. Si imponemos el valor de C1=100pF => R1=680Ohm; con esos valores la fc de ese filtro es cercana a 3,2MHz.
 
Queria contarles, me puse a probar contra un grafico de frecuencia en proteus (es lo que tengo) y cambiando los valores de los componentes segun el esquema que adjunto logre:

- Respuesta plana en frecuencia con 0db desde 1hz hasta ~2mhz
- Fcorte con -3db alrededor de los 2Mhz
- Aumentar de 5K1 a 47K las resistencias de la entrada analogica.

Con estos cambios, la señal se ve mejor. No es tan perfecta como la que se ve en el OCR de cosme (tiene apenas un poco mas de ruido porque falta filtro) pero no veo armonicos de baja frecuencia. Tengo que hacer mas pruebas

Lo que si, voy a tener que aumentar la resistencia que determina la ganancia del ultimo operacional, porque sigo teniendo una señal de 3.8vpp en vez de 5vpp

Tambien a partir de 1mhz la señal empieza a tener atenuacion. Aun me queda determinar si la causa es la frecuencia de corte, o la otra causa probable es que a partir de ciertos valores de prescaler, el generador saltea muestras de las 256 que hay en RAM. Dicho salteo casi seguro esta tomando samples de valores mas chicos, provocando efecto de atenuacion. Para solucionarlo, creo que voy a tener que hacer varios "sets" de samples en ram para elegir el mas adecuado de acuerdo a la F de salida esperada.

En este momento, estoy trabajando en la interfaz de usuario, le saque el teclado (era muy voluminoso) y estoy haciendo una interfaz a traves de un potenciometro como hizo cosme en su diseño.

Tambien le implemente en el hard y soft un frecuencimetro que mide la F de salida y realiza correcciones en el prescaler para mantenerla, pero luego quite esto y lo deje como visualizacion nomas, ya que no fue necesario que haga un "lock" automatico de la frecuencia. (es estable de por si)

Eso nomas, queria no dejar de comentar como me habia ido con los cambios :)
 

Adjuntos

  • siggen-hardware-analisis.pdf
    20.6 KB · Visitas: 18
Última edición:
Cosme,

Estuve avanzando en el generador de señal mio y ya casi esta para meter en gabinete.

Me meti aca para comentarte: Al mio le implemente un encoder rotativo, sacado de la ruedita del medio de un mouse. Es muy sencillo de implementar y me permitio hacer un menu para seleccion de frecuencia y muchas otras funciones muy facilmente

Era para darte la idea nomas. Un abrazo.
 
Atrás
Arriba