mirror of
				https://github.com/f4exb/sdrangel.git
				synced 2025-11-03 13:11:20 -05:00 
			
		
		
		
	Web API: example script to run LimeSDR in Tx mode. Updated main readme
This commit is contained in:
		
							parent
							
								
									bf1771f8d6
								
							
						
					
					
						commit
						19426a4536
					
				@ -105,7 +105,9 @@ HackRF is better used with a sampling rate of 4.8 MS/s and above. The 2.4 and 3.
 | 
			
		||||
 | 
			
		||||
<p><b>⚠ The plugins should work normally when running as single instances. Support of many Rx and/or Tx instances running concurrently is considered experimental.</b></p>
 | 
			
		||||
 | 
			
		||||
You will need a minimal installation of LimeSuite. Presently version 17.12.1 should be used with its corresponding firmware (v4) and gateware (v2.12) installed in the LimeSDR device:
 | 
			
		||||
<p>⚠ It seems LimeSDR mini has trouble working with host sample rates lower than 3 MS/s particularly in Tx mode.</p>
 | 
			
		||||
 | 
			
		||||
You will need a minimal installation of LimeSuite. Presently commit 04b57e0 or later should be used with its corresponding firmware (v4) and gateware (v2.12) installed in the LimeSDR device:
 | 
			
		||||
 | 
			
		||||
  - `sudo apt-get install libsqlite3-dev`
 | 
			
		||||
  - `git clone https://github.com/myriadrf/LimeSuite.git`
 | 
			
		||||
 | 
			
		||||
@ -35,6 +35,33 @@ It uses the following APIs:
 | 
			
		||||
    - URI: `/sdrangel/deviceset/{deviceSetIndex}/device/run`
 | 
			
		||||
    - HTTP method: `POST`
 | 
			
		||||
  
 | 
			
		||||
<h2>limesdr_tx.py</h2>
 | 
			
		||||
 | 
			
		||||
Create a Tx device set with a LimeSDR Tx device and a NFM modulator channel configured to send some beacon Morse code. Then starts the Tx.
 | 
			
		||||
 
 | 
			
		||||
It uses the following APIs:
 | 
			
		||||
 | 
			
		||||
  - To create a new device set:
 | 
			
		||||
    - OperationID: `instanceDeviceSetsPost`
 | 
			
		||||
    - URI: `/sdrangel/devicesets`
 | 
			
		||||
    - HTTP method: `POST`
 | 
			
		||||
  - To select a device in a device set:
 | 
			
		||||
    - Operation ID: `devicesetDevicePut`
 | 
			
		||||
    - URI: `/sdrangel/deviceset/{deviceSetIndex}/device`
 | 
			
		||||
    - HTTP method: `PUT`
 | 
			
		||||
  - To create a new channel:
 | 
			
		||||
    - Operation ID: `devicesetChannelPost`
 | 
			
		||||
    - URI: `/sdrangel/deviceset/{deviceSetIndex}/channel`
 | 
			
		||||
    - HTTP method: `POST`
 | 
			
		||||
  - To change the settings of a channel:
 | 
			
		||||
    - OperationID: `devicesetChannelSettingsPatch`
 | 
			
		||||
    - URI: `/sdrangel/deviceset/{deviceSetIndex}/channel/{channelIndex}/settings`
 | 
			
		||||
    - HTTP method: `PATCH`
 | 
			
		||||
  - Start a device streaming
 | 
			
		||||
    - OperationID: `devicesetDeviceRunPost`
 | 
			
		||||
    - URI: `/sdrangel/deviceset/{deviceSetIndex}/device/run`
 | 
			
		||||
    - HTTP method: `POST`
 | 
			
		||||
  
 | 
			
		||||
<h2>nfm_test.py</h2>
 | 
			
		||||
 | 
			
		||||
Example of creating NFM channels (demodulator and modulator) and changing the settings
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										109
									
								
								swagger/sdrangel/examples/limesdr_tx.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										109
									
								
								swagger/sdrangel/examples/limesdr_tx.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,109 @@
 | 
			
		||||
#!/usr/bin/env python
 | 
			
		||||
 | 
			
		||||
import requests, json, traceback, sys
 | 
			
		||||
from optparse import OptionParser
 | 
			
		||||
 | 
			
		||||
base_url = "http://127.0.0.1:8091/sdrangel"
 | 
			
		||||
 | 
			
		||||
requests_methods = {
 | 
			
		||||
    "GET": requests.get,
 | 
			
		||||
    "PATCH": requests.patch,
 | 
			
		||||
    "POST": requests.post,
 | 
			
		||||
    "PUT": requests.put,
 | 
			
		||||
    "DELETE": requests.delete
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
# ======================================================================
 | 
			
		||||
def getInputOptions():
 | 
			
		||||
 | 
			
		||||
    parser = OptionParser(usage="usage: %%prog [-t]\n")
 | 
			
		||||
    parser.add_option("-a", "--address", dest="address", help="address and port", metavar="ADDRESS", type="string") 
 | 
			
		||||
 | 
			
		||||
    (options, args) = parser.parse_args()
 | 
			
		||||
    
 | 
			
		||||
    if (options.address == None):
 | 
			
		||||
        options.address = "127.0.0.1:8091"
 | 
			
		||||
    
 | 
			
		||||
    return options
 | 
			
		||||
 | 
			
		||||
# ======================================================================
 | 
			
		||||
def printResponse(response):
 | 
			
		||||
    content_type = response.headers.get("Content-Type", None)
 | 
			
		||||
    if content_type is not None:
 | 
			
		||||
        if "application/json" in content_type:
 | 
			
		||||
            print(json.dumps(response.json(), indent=4, sort_keys=True))
 | 
			
		||||
        elif "text/plain" in content_type:
 | 
			
		||||
            print(response.text)
 | 
			
		||||
 | 
			
		||||
# ======================================================================
 | 
			
		||||
def callAPI(url, method, params, json, text):
 | 
			
		||||
    request_method = requests_methods.get(method, None)
 | 
			
		||||
    if request_method is not None:
 | 
			
		||||
        r = request_method(url=base_url+url, params=params, json=json)
 | 
			
		||||
        if r.status_code == 200:
 | 
			
		||||
            print(text + " succeeded")
 | 
			
		||||
            printResponse(r)
 | 
			
		||||
            return r.json() # all 200 yield application/json response
 | 
			
		||||
        else:
 | 
			
		||||
            print(text + " failed")
 | 
			
		||||
            printResponse(r)
 | 
			
		||||
            return None
 | 
			
		||||
 | 
			
		||||
# ======================================================================
 | 
			
		||||
def main():
 | 
			
		||||
    try:
 | 
			
		||||
        options = getInputOptions()
 | 
			
		||||
        
 | 
			
		||||
        global base_url
 | 
			
		||||
        base_url = "http://%s/sdrangel" % options.address
 | 
			
		||||
        
 | 
			
		||||
        r = callAPI("/devicesets", "POST", {"tx": 1}, None, "Add Tx device set")
 | 
			
		||||
        if r is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
            
 | 
			
		||||
        r = callAPI("/deviceset/1/device", "PUT", None, {"hwType": "LimeSDR", "tx": 1}, "setup LimeSDR on Tx 1")
 | 
			
		||||
        if r is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
            
 | 
			
		||||
        settings = callAPI("/deviceset/1/device/settings", "GET", None, None, "Get LimeSDR Tx settings")
 | 
			
		||||
        if settings is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
 | 
			
		||||
        settings["limeSdrOutputSettings"]["antennaPath"] = 1
 | 
			
		||||
        settings["limeSdrOutputSettings"]["devSampleRate"] = 3200000
 | 
			
		||||
        settings["limeSdrOutputSettings"]["log2SoftInterp"] = 4
 | 
			
		||||
        settings["limeSdrOutputSettings"]["ncoEnable"] = 1
 | 
			
		||||
        settings["limeSdrOutputSettings"]["ncoFrequency"] = -500000
 | 
			
		||||
        settings["limeSdrOutputSettings"]["lpfFIRBW"] = 100000
 | 
			
		||||
        settings["limeSdrOutputSettings"]["lpfFIREnable"] = 1 
 | 
			
		||||
        
 | 
			
		||||
        r = callAPI("/deviceset/1/device/settings", "PATCH", None, settings, "Patch LimeSDR Tx settings")
 | 
			
		||||
        if r is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
            
 | 
			
		||||
        settings = callAPI("/deviceset/1/channel", "POST", None, {"channelType": "NFMMod", "tx": 1}, "Create NFM mod")
 | 
			
		||||
        if settings is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
        
 | 
			
		||||
        settings["NFMModSettings"]["cwKeyer"]["text"] = "VVV DE F4EXB  "
 | 
			
		||||
        settings["NFMModSettings"]["cwKeyer"]["loop"] = 1
 | 
			
		||||
        settings["NFMModSettings"]["cwKeyer"]["mode"] = 1 # text
 | 
			
		||||
        settings["NFMModSettings"]["modAFInput"] = 4 # CW text
 | 
			
		||||
        settings["NFMModSettings"]["toneFrequency"] = 600
 | 
			
		||||
        
 | 
			
		||||
        r = callAPI("/deviceset/1/channel/0/settings", "PATCH", None, settings, "Change NFM mod")
 | 
			
		||||
        if r is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
            
 | 
			
		||||
        r = callAPI("/deviceset/1/device/run", "POST", None, None, "Start device on deviceset R1")
 | 
			
		||||
        if r is None:
 | 
			
		||||
            exit(-1)
 | 
			
		||||
        
 | 
			
		||||
    except Exception, msg:
 | 
			
		||||
        tb = traceback.format_exc()
 | 
			
		||||
        print >> sys.stderr, tb
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
if __name__ == "__main__":
 | 
			
		||||
    main()
 | 
			
		||||
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user