27 decembrie 2015

Arduino and SI4713 FM Stereo RDS transmitter

I was playing with this circuit but the audio was crap.
Looking into the circuit's datasheet I found that this is a real treasure by having a lot of option which are left unexplored like audio AGS, a very smart audio compressor with the possibility to fine tune the parameters and so on.
So, I was thinking what if I setup more parameters than in the AdaFruit example?
The simplest way to do so was to look into the datasheet and into a very nice document (also from SI Labs) which explain various settings, especially that used for audio path, and sent the commands directly via I2C.
It was just too complicated to write new libraries... I am not so smart!

Here is the code. Please, mention me if you use it.



   /* Astea sunt comenzi trimise catre SI4713 direct prin I2C si regleaza tot ce e de reglat astfel incat transmitatorul sa
   furnizeze un semnal compatibil cu receptoarele europene, folosind si etajele de limitare si compresie incorporate in
   circuit.
   Valorile din registri au fost alese pentru semnal dintr-un mp3 player.
   Copyright 2015, YO3HJV, Adrian
   */

   /*
   The setiings are sent to SI4713 directly via I2C commands and not via the Arduino library. The commands are documented in the SI4713 datasheet.
   The audio settings for the limiter and AGS are documented in "AN332.pdf".
   Copyright 2015, YO3HJV, Adrian
   */

   // The transmitter's frequency was previously programmed via the AdaFruit example .ino
  
  
        #include <Wire.h>


   
       

        void setup() {
               
          // RESET, wait then POWERUP and wait then SET
         
               pinMode(12, OUTPUT);
               digitalWrite(13, LOW);
               delay(100);
               digitalWrite(12, HIGH);
               delay(5);
               powerup();
              
               setClock();         
               tune();
               multiplex();
               preemphasys();
            
               compEnable();
               compsm();
               limiterrelease();
               deviation();            
               setpower();
               level();  
              
              
                
              
                     }



         void loop()  {                      
                
                      }
        
         void setClock()   {
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x02);                                  //
                              Wire.write(0x01);                                  //
                              Wire.write(0x7E);                                  //
                              Wire.write(0xF4);                                  //
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                            }
          
          
 
          
         void powerup()    {
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x01);                                  // sends register address
                              Wire.write(0xC2);                                  // sends register data
                              Wire.write(0x50);                                  //
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                            }
        
        
         void limiterrelease() {
              //  TX_LIMITER_RELEASE_TIME 39.38 ms)
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  //
                              Wire.write(0x05);                                  // TX_LIMITER_RELEASE_TIME
                              Wire.write(0x00);                                  // Sets the limiter release time to 13 (39.38 ms)
                              Wire.write(0x0D);                                  //
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                               }
                 
                              
          
         void  compsm()  {    // Smooth Compression
                 //  TX_ACOMP_THRESHOLD    -40db
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  //
                              Wire.write(0x01);                                  // TX_ACOMP_THRESHOLD
                              Wire.write(0xFF);                                  // Threshold = –40 dBFS = 0xffd8
                              Wire.write(0xD8);                                  //
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                            
                 // TX_ACOMP_ATTACK_TIME = 5 ms
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  //
                              Wire.write(0x02);                                  // TX_ACOMP_ATTACK_TIME
                              Wire.write(0x00);                                  //
                              Wire.write(0x02);                                  // Attack time = 1.5 ms = 2 STEP: 0.5 msec
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                             
                 // TX_ACOMP_RELEASE_TIME = 100 ms
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  //
                              Wire.write(0x03);                                  // TX_ACOMP_RELEASE_TIME
                              Wire.write(0x00);                                  //
                              Wire.write(0x02);                                  // Release time = 1000 ms = 4 STEP: 250ms
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                             
                 // TX_ACOMP_GAIN = 15 dB
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x12);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  //
                              Wire.write(0x04);                                  // TX_ACOMP_GAIN
                              Wire.write(0x00);                                  //
                              Wire.write(0x0F);                                  //
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);
                       }

              void tune()  {
                              Wire.beginTransmission(0x63);                      // transmit to device 0x63
                              Wire.write(0x30);                                  // sends register address
                              Wire.write(0x00);                                  // sends register data
                              Wire.write(0x22);                                  // Set frequency in HEX
                              Wire.write(0x2E);                                  // 96.50 >>> 9650 = 25B2 in HEX
                              Wire.endTransmission();                            // stop transmitting
                              delay(5);                                          // allow register to set
                            }
                
              void deviation() {                                            // max dev 68.25 kHz >>> 6825 to Hex: 1AA9
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x12);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x21);                                // sends register data
                              Wire.write(0x01);                                // sends register data
                              Wire.write(0x1A);                                // Max deviation 68.00
                              Wire.write(0x90);                                // 1A90
                              Wire.endTransmission();                          // stop transmitting
                              delay(5);                                        // allow register to set                                
                               }
                              
              void compEnable() {                                            //
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x12);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x22);                                // sends register data
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x00);                                //                              
                              Wire.write(0x03);                                // 
                              Wire.endTransmission();                          // stop transmitting
                              delay(5);                                        // allow register to set                                
                                 }

      
                
              void level()  {
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x12);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x21);                                // sends register data
                              Wire.write(0x04);                                // sends register data
                              Wire.write(0x21);                                // sends register data
                              Wire.write(0x96);                                // Max input 150mV pk
                              Wire.endTransmission();                          // stop transmitting
                            }
                
              void preemphasys() {
                       
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x12);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x21);                                // sends register data
                              Wire.write(0x06);                                // sends register data
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x01);                                //  50 uSec for Europe
                              Wire.endTransmission();                          // stop transmitting
                              delay(5); 
                                 }
                                
              void multiplex()  {
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x12);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x21);                                // sends register data
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x03);                                //
                              Wire.endTransmission();                          // stop transmitting
                                }
                                
              void setpower()    {
                              Wire.beginTransmission(0x63);                    // transmit to device 0x63
                              Wire.write(0x31);                                // sends register address
                              Wire.write(0x00);                                // sends register data
                              Wire.write(0x00);                                // Power
                              Wire.write(0x73);                                // to 115 dBuV
                              Wire.write(0x00);                                // Antenna capacitor to AUTO
                              Wire.endTransmission();                          // stop transmitting
                              delay(5); 

                                 }

//  END OF CODE //



Of course, this is here because a tend to forget where I save documents!

Interesting implementation for the free frequency here:
https://forum.arduino.cc/index.php?topic=261189.0

23 decembrie 2015

"Summits On The Air" in Romania - din culise


Summits On The Air - Romania In 2008 am dat pe net peste un program de legaturi radio interesante, facute de radioamatori care se duceau cu statia in regim portabil pe cate un varf de munte si de acolo faceau legaturi in toata lumea in unde scurte (HF) sau in ultrascurte, cu statii mai apropiate.

Mi s-a parut tare interesant si mai ca m-as fi bagat si eu in treaba asta, asa ca am stat si am citit cam tot ce era de citit pe site-ul SOTA

In doua cuvinte, SOTA este o activitate care imbina radioamatorismul cu urcatul pe munti cu statioara dupa tine, batut in cuie de radioamatorii britanici prin anul 2002.

La vremea cand citeam pentru prima data ce ce si cum despre SOTA, lista de tari prezenta pe site era destul de restransa dar si asa, sugera o companie selecta.
Am citit si tot citit si, pana la urma, am scris cateva randuri pe forumularul de contact de pe site. Mi-a raspuns un membru al echipei care se ocupa de afilierea noilor tari in program, denumite in limbajul SOTA "Asociatii". Era Les Allwood, G3VQO.

Asa am aflat ca nu e chiar asa simplu sa lucrezi ca activator de varfuri din Romania, ca inainte de a te urca pe acel varf, el trebuie sa fie cumva omologat prin includerea intr-un document intocmit dupa niste reguli stricte iar proeminenta sa sa fie validata printr-o metoda stiintifica de observare.
Am invatat deci, despre SRTM (Shuttle Radar Topography Mission) care a fost un program complex de cartografiere 3D a suprafetei Pamantului realizat cu ajutorul unui radar interferometric cu apertura sintetica instalat pe naveta spatiala Endeavor si multe alte nazdravanii din astea, dar care nu ma ajutau prea mult,  caci regulile programului SOTA spuneau, in esenta, ca varfurile trebuie sa fie caracterizate printr-o proeminenta bine determinata in raport de geografia inconjuratoare dar, extrem de important, ele trebuie sa fie prezente pe harti turistice!

In Romania nu au fost prea multe surse de asemenea harti si imi aduc aminte de adolescenta mea de montaniard (ca altceva nu prea aveai ce face vara, toamna, iarna prin vacante decat sa pleci sa dai ture pe munte cu prietenii. Acuma se dau pe feisbuk, TNX ZaharMunte!)

Am facut o colectie mare de link-uri cu site-uri pe care mai apareau tot felul de harti scanate, de ture inregistrate cu GPS-uri si alte asemenea aproximari. Ba chiar am reusit, la un moment dat, sa fac rost de un DVD cu niste harti militare extraordinar de precise dar realizate cu mijloace topometrice clasice si impanate cu simboluri caracteristice de parca citeam panoul de bord al navei spatiale cu care au sosit Predatori-i!

"Rasfoind" corespondenta pe tema SOTA, am aflat si data la care i-am scris: 19 iulie 2008. Geez, parca a trecut o viata de atunci! Era in perioada cand se nastea si SRR si chiar am discutat cu Les daca aceasta "SOTA YO Association" necesita o formalizare legala sau nu.
Din fericire, mi-a raspuns ca nu este necesara si ca "Asociatia" reprezinta setul de reguli si suma varfurilor, ceea ce cred eu ca este OK intrucat, la acel moment, prioritara era inscrierea varfurilor din Romania pe lista prezenta pe site-ul SOTA si mai putin chestiunile ce tin de asociatii care, in Romania, nasc pasiuni si strica prietenii.

Printre sfaturile pe care mi le-a dat Les au fost unele care vizau popularizarea programului si cresterea interesului radioamatorilor din YO fata de acest program.

Am facut deci, o pagina de blog dedicata SOTA Romania  ai am mai scris pe ici si colo cate ceva referitor la aceasta activitate, pornind si un grup de discutii pe yahoo in speranta ca vom reusi sa ne strangem mai multi radioamatori si sa colaboram pentru a realiza rapid lista de varfuri.
Am inceput sa fac un tabel cu varfurile pe care le-am identificat din diverse surse, in special harti turistice scanate, apoi sa le gasesc coordonatele si altitudinea pe Google Earth.
Pornind de la exemplul altor tari si de la un model de ARM (Association Reference Manual), documentul la care se raporteaza activitatea SOTA dintr-o anume tara, m-am gandit sa impart muntii exact asa cum i-am invatat la Geografie prin scoala sau liceu, Orientali, Meridionali, Occidentali si Muntii Macin. 

Intre timp, am mai trimis  email-uri la radioamatori pe care i-am observat interesati de activitati de portabil HF in speranta ca ne vom strange laolalta sa dovedim intocmirea listei, am avut discutii cu alti cativa la Simpozionul de la Alba Iulia din 2008 (parca);  din pacate insa, marea majoritate s-a "pierdut" pe drum.

Ma gandisem chiar ca, pentru fiecare zona voi gasi cativa radioamatori care sa sprijine corelarea varfurilor notate pe harti cu cele de pe lista cu proeminente SRTM transmisa de Les si apoi sa le verifice cu Google Earth, eventual cu coordonate GPS preluate chiar de la diversi alpinisti si montaniarzi.

Munca de Sisif, pe un ecran de 12 inch. Apoi, Les mi-a transmis o lista obtinuta prin filtrarea datelor SRTM cu ajutorul programului Landserf, dar cu mentiunea ca datele nu au precizia necesara si, deci, este nevoie sa fie verificate pe teren, harti sau Google Maps. Erau circa 1200 de varfuri ce se calificau mai mult sau mai putin. Asta era prin 2009 cand datele SRTM nu aveau precizia de acum, in mod intentionat. Deh, secret militar SUA.

Fac o scurta paranteza si postez un extras din lista transmisa:
YO ref ARM ref          Long               Lat                   Ht (m) Prom (m)        Comments                

....
            1083                27.242490       46.940160                   157     
            1084                27.267452       46.579360                   236     
            1085                27.360313       47.008476                   214     
            1086                27.514668       46.976086                   152     
            1087                27.673378       47.030502                   185     
            1088                27.832722       46.210020                   150     
            1089                27.923279       46.935017                   200     
            1090                28.021425       45.969860                   209     
            1091                28.201944       45.107937                   216     
            1092                28.255781       45.121710                   159     
            1093                28.264536       45.205185                   428     
            1094                28.439688       45.119540                   218     
            1095                28.448069       44.904163                   221     
            1096                28.512281       45.023210                   200     
            1097                28.690035       44.998764                   204     
Procedura era urmatoarea:
Fiecare varf se transfera in Google Earth. Apoi, cautam o harta a zonei in functie de localitatile pe care le gaseam pe GE. Pe harta respectiva, incercam sa identific denumirea varfului.
Tineti cont ca ultimul numar din lista indica proeminenta, adica inaltimea relativa fata de geografia inconjuratoare si nu altitudinea! Altitudinea urma sa o inscriu eu pe tabelul care urma sa arate asa:
YO ref ARM ref          Long   Lat       Ht (m) Prom (m)        Comments                

            485      EC-001            24.258780       47.520430       1840    1047   
                        EC-003            23.842610       47.703540       1443                move to 415
            553      EC-004            24.636521       47.589472       2120    1975   
                        EC-005            24.715933       47.726579       1890                move to 569
                        EC-006            25.104160       47.481660       1787    675+   
                        EC-007            25.152530       47.118810       1882                move to 692
                        EC-008            25.191211       46.846140       1588                move to 701
                        EC-009            26.065142       46.494524       1664    900+   
                        EC-010            25.748700       46.491780       2287                not a summit - misplotted?
                        EC-011            25.620221       46.139701       1746                not a summit - misplotted?
            766      EC-012            25.484031       47.434261       1859    749     
                        EC-013            25.566610       47.440800       1651                move to 791
                        EC-014            25.845250       46.860060       1373                non-compliant

Repetati asta pentru fiecare din varfurile din ARM...

Dupa, tabelul xls se trimitea la Les, el il verifica, gasea abateri fata de Landserf si returna cu observatii :-). Discutii, trimite harta, trimite punctul pe GE etc. Enspe mii de variante de xls colorate diferit iar eu am o afurisita de discromatopsie!

Intre timp, s-au pus la dispozitia publicului date SRTM de precizie mai mare si multe varfuri au fost din nou luate la puricat tocmai cand credeam ca e gata si iesim in lume!

Prima editie a ARM pentru Romania a fost publicata pe site-ul SOTA la 1 aprilie 2010, cu mult inaintea altor tari in care comunitatea radioamatorilor implicati in diverse proiecte comune este mult mai puternica si asta chiar a fost un motiv de mandrie pentru noi, adica pentru mine si pentru Zoli, YO2BP care a fost de un mare ajutor atat la lista propriu-zisa cat si din punct de vedere moral. Mai era un nebun (in sensul bun, zic eu) care credea in programul acesta si care isi pierdea vremea sa scrie liste de varfuri!

Aproape doi ani a durat "aventura" inscrierii Romaniei radioamatorilor in programul SOTA, uneori regret ca exact in aceasta perioada pustoaica mea crestea iar eu stateam noptile si in fiecare moment liber puricand listele dar, una peste alta, cred ca a meritat.

Google Earth Romanian Summits on SOTA O vreme, SOTA a cam lancezit si mare lucru nu se intampla insa, incet incet, au inceput sa apara activatori YO si, din fericire, Csaba YO5PIB s-a implicat puternic in partea "administrativa" a programului SOTA-YO, reusind sa actualizam lista de varfuri incrise in SOTA ajungand la a doua editie a ARM-SOTA-YO  sa avem peste 1000 de varfuri, cum previziona Zoli prin 2008!
Din pacate, unele probleme de sanatate m-au impiedicat sa iau parte la activitatile SOTA asa cum mi-as fi dorit dar voi incerca sa recuperez usor usor.

Am fost dezamagit de unele remarci pe ici pe colo prin internetul asta mare si am mai fost dezamagit de incercarea de a confisca acest program de catre unii sau altii. Imi aduc aminte de spiritul oamenilor care petrec timp pe munte: nu sunt chiar asa usor de dus de nas si asta ma face sa cred ca SOTA-YO isi va gasi propriul drum.

73 de Adrian, YO3HJV

22 decembrie 2015

Portable HF antenna setup

Well, the winter is coming (at least when I peek to the calendar) so it's time to make the antennas for portable HF.
I am using an ICOM IC-703+ with the ICOM backpack and a vertical Racal antenna. But this is not enough for me so I planned to experiment with an End Fed antenna.
I contemplated the End Fed Half Wave antenna with a high ratio UnUn but the tests I did on my lab didn't convince me. I also find the lenght of the EFHW not suitable for what I expect from a portable setup. It's simply to lenghty to use it on various setups, mainly to keep it at the necessary height from the ground.
So, the next choice for a multiband wire antenna is also some sort of End Fed but the one that can be fed with a 9:1 UnUn, an aperiodic one.
On the internet there are several places where you cand found a suitable lenght for the wire.
As I am not interested on 160m band from portable, I choose the 13.5 m as the best for me.
I quickly made a 9:1 Unbalanced to Unbalanced broadband transformer and a 1:1 choke Balun made from a piece of RG316 teflon coax on a FT-120-43 toroid core. This consist of 4+4 turns on the ferrite core.
I prepared two pieces of RG58 coax cable. One of 10m and the second one of 5m.
I can use the choke balun to make a counterpoise from the 5 or from the 10m of coax cable. If the conditions permit, I cand put a real counterpoise directly on the 9:1 BalUn and use the entire lenght of the cable with a UHF Female-female adapter without the choke balun. Or even to use the choke balun right at the transceiver's output.
So, I believe this setup let me experiment in the field with the best setup from various ones.
I will revisit this post after the Christmas holiday.
Merry Christmas!

 I forgot, this is a small Z-Match made with polyvaricons. This is to be used with 450 Ohm ladder line and simmetrical dipoles.


QRP Z-matchbox


9:1 QRP Bal-Un

Prerequisites for 1:1 choke balun



9:1 BalUn inside

9:1 BalUn inside


Portable EndFed setup

Portable EndFed setup

Portable EndFed setup - detail

Most viewed posts in last 30 days