added rx888

This commit is contained in:
Ryzerth 2020-11-12 00:53:38 +01:00
parent 0a5fd5c271
commit 02ae50905d
37 changed files with 6038 additions and 85 deletions

View File

@ -8,6 +8,8 @@ add_subdirectory("recorder")
add_subdirectory("soapy")
add_subdirectory("file_source")
add_subdirectory("rtl_tcp_source")
# add_subdirectory("audio_sink")
add_subdirectory("rx888_source")
add_subdirectory("demo")
if (MSVC)

16
audio_sink/CMakeLists.txt Normal file
View File

@ -0,0 +1,16 @@
cmake_minimum_required(VERSION 3.13)
project(audio_sink)
if (MSVC)
set(CMAKE_CXX_FLAGS "-O2 /std:c++17")
else()
set(CMAKE_CXX_FLAGS "-O3 -std=c++17 -fpermissive")
endif (MSVC)
file(GLOB SRC "src/*.cpp")
include_directories("src/")
add_library(audio_sink SHARED ${SRC})
target_link_libraries(audio_sink PRIVATE sdrpp_core)
set_target_properties(audio_sink PROPERTIES PREFIX "")

66
audio_sink/src/main.cpp Normal file
View File

@ -0,0 +1,66 @@
#include <imgui.h>
#include <module.h>
#include <gui/gui.h>
#include <signal_path/signal_path.h>
#include <signal_path/sink.h>
#define CONCAT(a, b) ((std::string(a) + b).c_str())
class AudioSink : SinkManager::Sink {
public:
AudioSink(SinkManager::Stream* stream) {
_stream = stream;
}
~AudioSink() {
}
void menuHandler() {
}
private:
SinkManager::Stream* _stream;
};
class AudioSinkModule {
public:
AudioSinkModule(std::string name) {
this->name = name;
provider.create = create_sink;
provider.ctx = this;
sigpath::sinkManager.registerSinkProvider("Audio", provider);
}
~AudioSinkModule() {
}
private:
static SinkManager::Sink* create_sink(SinkManager::Stream* stream, void* ctx) {
return (SinkManager::Sink*)(new AudioSink(stream));
}
std::string name;
SinkManager::SinkProvider provider;
};
MOD_EXPORT void _INIT_() {
// Nothing here
}
MOD_EXPORT void* _CREATE_INSTANCE_(std::string name) {
AudioSinkModule* instance = new AudioSinkModule(name);
return instance;
}
MOD_EXPORT void _DELETE_INSTANCE_() {
}
MOD_EXPORT void _STOP_() {
}

View File

@ -1,5 +1,6 @@
#pragma once
#include <dsp/block.h>
#include <volk/volk.h>
#include <spdlog/spdlog.h>
@ -138,6 +139,14 @@ namespace dsp {
volk_32fc_magnitude_32f(out.data, (lv_32fc_t*)_in->data, count);
_in->flush();
volk_32f_accumulator_s32f(&avg, out.data, count);
avg /= (float)count;
for (int i = 0; i < count; i++) {
out.data[i] -= avg;
}
out.write(count);
return count;
}
@ -145,6 +154,7 @@ namespace dsp {
stream<float> out;
private:
float avg;
int count;
stream<complex_t>* _in;

View File

@ -1,8 +1,7 @@
#pragma once
#include <dsp/block.h>
#include <dsp/window.h>
#include <spdlog/spdlog.h>
#include <string.h>
namespace dsp {

View File

@ -1,7 +1,7 @@
#pragma once
#include <dsp/block.h>
#include <spdlog/spdlog.h>
#include <fftw3.h>
#include <string.h>
namespace dsp {
class FrequencyXlator : public generic_block<FrequencyXlator> {
@ -75,4 +75,56 @@ namespace dsp {
stream<complex_t>* _in;
};
class AGC : public generic_block<AGC> {
public:
AGC() {}
AGC(stream<float>* in, float ratio) { init(in, ratio); }
~AGC() { generic_block<AGC>::stop(); }
void init(stream<float>* in, float ratio) {
_in = in;
_ratio = ratio;
generic_block<AGC>::registerInput(_in);
generic_block<AGC>::registerOutput(&out);
}
void setInputSize(stream<float>* in) {
std::lock_guard<std::mutex> lck(generic_block<AGC>::ctrlMtx);
generic_block<AGC>::tempStop();
generic_block<AGC>::unregisterInput(_in);
_in = in;
generic_block<AGC>::registerInput(_in);
generic_block<AGC>::tempStart();
}
int run() {
count = _in->read();
if (count < 0) { return -1; }
if (out.aquire() < 0) { return -1; }
for (int i = 0; i < count; i++) {
level = (fabsf(_in->data[i]) * _ratio) + (level * (1.0f - _ratio));
out.data[i] = _in->data[i] / level;
}
_in->flush();
out.write(count);
return count;
}
stream<float> out;
private:
int count;
float level = 1.0f;
float _ratio;
stream<float>* _in;
};
}

View File

@ -2,6 +2,7 @@
#include <dsp/block.h>
#include <dsp/window.h>
#include <numeric>
#include <string.h>
namespace dsp {
template <class T>

View File

@ -1,7 +1,7 @@
#pragma once
#include <dsp/block.h>
#include <dsp/buffer.h>
#include <cstring>
#include <string.h>
#include <numeric>
#include <spdlog/spdlog.h>

View File

@ -27,7 +27,7 @@ namespace dsp {
void setCutoff(float cutoff) {
_cutoff = cutoff;
}
void setTransWidth(float transWidth) {
_transWidth = transWidth;
}

42
core/src/event.h Normal file
View File

@ -0,0 +1,42 @@
#pragma once
#include <vector>
#include <spdlog/spdlog.h>
template <class T>
class Event {
public:
Event() {}
~Event() {}
struct EventHandler {
EventHandler(void (*handler)(T, void*), void* ctx) {
this->handler = handler;
this->ctx = ctx;
}
void (*handler)(T, void*);
void* ctx;
};
void emit(T value) {
for (auto const& handler : handlers) {
handler.handler(value, handler.ctx);
}
}
void bindHandler(const EventHandler& handler) {
handlers.push_back(handler);
}
void unbindHandler(const EventHandler& handler) {
if (handlers.find(handler) == handlers.end()) {
spdlog::error("Tried to remove a non-existant event handler");
return;
}
handlers.erase(std::remove(handlers.begin(), handlers.end(), handler), handlers.end());
}
private:
std::vector<EventHandler> handlers;
};

View File

@ -7,13 +7,8 @@
#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include <imgui_plot.h>
#include <dsp/resampling.h>
#include <dsp/demodulator.h>
#include <dsp/filter.h>
#include <thread>
#include <complex>
#include <dsp/source.h>
#include <dsp/math.h>
#include <gui/waterfall.h>
#include <gui/frequency_select.h>
#include <fftw3.h>

View File

@ -1,13 +1,8 @@
#pragma once
#include <dsp/filter.h>
#include <dsp/resampling.h>
#include <dsp/source.h>
#include <dsp/math.h>
#include <dsp/demodulator.h>
#include <dsp/routing.h>
#include <dsp/sink.h>
#include <dsp/vfo.h>
#include <map>
#include <dsp/sink.h>
#include <module.h>
class SignalPath {

View File

@ -4,4 +4,5 @@ namespace sigpath {
SignalPath signalPath;
VFOManager vfoManager;
SourceManager sourceManager;
SinkManager sinkManager;
};

View File

@ -2,10 +2,12 @@
#include <signal_path/dsp.h>
#include <signal_path/vfo_manager.h>
#include <signal_path/source.h>
#include <signal_path/sink.h>
#include <module.h>
namespace sigpath {
SDRPP_EXPORT SignalPath signalPath;
SDRPP_EXPORT VFOManager vfoManager;
SDRPP_EXPORT SourceManager sourceManager;
SDRPP_EXPORT SinkManager sinkManager;
};

View File

@ -0,0 +1,98 @@
#include <signal_path/sink.h>
#include <spdlog/spdlog.h>
#include <core.h>
SinkManager::SinkManager() {
}
SinkManager::Stream::Stream(dsp::stream<dsp::stereo_t>* in, const Event<float>::EventHandler& srChangeHandler, float sampleRate) {
_in = in;
srChange.bindHandler(srChangeHandler);
_sampleRate = sampleRate;
splitter.init(_in);
}
void SinkManager::Stream::setInput(dsp::stream<dsp::stereo_t>* in) {
std::lock_guard<std::mutex> lck(ctrlMtx);
_in = in;
splitter.setInput(_in);
}
dsp::stream<dsp::stereo_t>* SinkManager::Stream::bindStream() {
dsp::stream<dsp::stereo_t>* stream = new dsp::stream<dsp::stereo_t>;
splitter.bindStream(stream);
return stream;
}
void SinkManager::Stream::unbindStream(dsp::stream<dsp::stereo_t>* stream) {
splitter.unbindStream(stream);
delete stream;
}
void SinkManager::Stream::setSampleRate(float sampleRate) {
std::lock_guard<std::mutex> lck(ctrlMtx);
_sampleRate = sampleRate;
srChange.emit(sampleRate);
}
void SinkManager::registerSinkProvider(std::string name, SinkProvider provider) {
if (providers.find(name) != providers.end()) {
spdlog::error("Cannot create sink provider '{0}', this name is already taken", name);
return;
}
providers[name] = provider;
}
void SinkManager::registerStream(std::string name, SinkManager::Stream* stream) {
if (streams.find(name) != streams.end()) {
spdlog::error("Cannot register stream '{0}', this name is already taken", name);
return;
}
core::configManager.aquire();
std::string providerName = core::configManager.conf["defaultSink"];
core::configManager.release();
SinkManager::SinkProvider provider;
if (providers.find(providerName) == providers.end()) {
// TODO: get default
}
else {
provider = providers[providerName];
}
stream->sink = provider.create(stream, provider.ctx);
}
void SinkManager::unregisterStream(std::string name) {
if (streams.find(name) == streams.end()) {
spdlog::error("Cannot unregister stream '{0}', this stream doesn't exist", name);
return;
}
SinkManager::Stream* stream = streams[name];
delete stream->sink;
delete stream;
}
dsp::stream<dsp::stereo_t>* SinkManager::bindStream(std::string name) {
if (streams.find(name) == streams.end()) {
spdlog::error("Cannot bind to stream '{0}'. Stream doesn't exist", name);
return NULL;
}
return streams[name]->bindStream();
}
void SinkManager::unbindStream(std::string name, dsp::stream<dsp::stereo_t>* stream) {
if (streams.find(name) == streams.end()) {
spdlog::error("Cannot unbind from stream '{0}'. Stream doesn't exist", name);
return;
}
streams[name]->unbindStream(stream);
}
void SinkManager::showMenu() {
for (auto const& [name, stream] : streams) {
}
}

View File

@ -0,0 +1,65 @@
#pragma once
#include <map>
#include <string>
#include <dsp/stream.h>
#include <dsp/types.h>
#include <dsp/routing.h>
#include <mutex>
#include <event.h>
class SinkManager {
public:
SinkManager();
class Sink {
public:
virtual void menuHandler() = 0;
};
class Stream {
public:
Stream(dsp::stream<dsp::stereo_t>* in, const Event<float>::EventHandler& srChangeHandler, float sampleRate);
void setInput(dsp::stream<dsp::stereo_t>* in);
dsp::stream<dsp::stereo_t>* bindStream();
void unbindStream(dsp::stream<dsp::stereo_t>* stream);
friend SinkManager;
friend SinkManager::Sink;
Event<float> srChange;
private:
void setSampleRate(float sampleRate);
dsp::stream<dsp::stereo_t>* _in;
dsp::Splitter<dsp::stereo_t> splitter;
SinkManager::Sink* sink;
std::mutex ctrlMtx;
float _sampleRate;
};
struct SinkProvider {
SinkManager::Sink* (*create)(SinkManager::Stream* stream, void* ctx);
void* ctx;
};
void registerSinkProvider(std::string name, SinkProvider provider);
void registerStream(std::string name, Stream* stream);
void unregisterStream(std::string name);
dsp::stream<dsp::stereo_t>* bindStream(std::string name);
void unbindStream(std::string name, dsp::stream<dsp::stereo_t>* stream);
void showMenu();
private:
// TODO: Replace with std::unordered_map
std::map<std::string, SinkProvider> providers;
std::map<std::string, Stream*> streams;
};

View File

@ -45,6 +45,8 @@ void SigPath::init(std::string vfoName, uint64_t sampleRate, int blockSize) {
amDemod.init(vfo->output);
ssbDemod.init(vfo->output, 6000, 3000, dsp::SSBDemod::MODE_USB);
agc.init(&amDemod.out, 1.0f / 125.0f);
audioWin.init(24000, 24000, 200000);
audioResamp.init(&demod.out, &audioWin, 200000, 48000);
audioWin.setSampleRate(audioResamp.getInterpolation() * 200000);
@ -82,6 +84,7 @@ void SigPath::setDemodulator(int demId, float bandWidth) {
demod.stop();
}
else if (_demod == DEMOD_AM) {
agc.stop();
amDemod.stop();
}
else if (_demod == DEMOD_USB) {
@ -139,7 +142,7 @@ void SigPath::setDemodulator(int demId, float bandWidth) {
else if (demId == DEMOD_AM) {
demodOutputSamplerate = 125000;
vfo->setSampleRate(12500, bandwidth);
audioResamp.setInput(&amDemod.out);
audioResamp.setInput(&agc.out);
audioBw = std::min<float>(bandwidth, outputSampleRate / 2.0f);
audioResamp.setInSampleRate(12500);
@ -150,6 +153,7 @@ void SigPath::setDemodulator(int demId, float bandWidth) {
deemp.bypass = true;
vfo->setReference(ImGui::WaterfallVFO::REF_CENTER);
agc.start();
amDemod.start();
}
else if (demId == DEMOD_USB) {

View File

@ -1,18 +1,13 @@
#pragma once
#include <dsp/filter.h>
#include <dsp/resampling.h>
#include <dsp/source.h>
#include <dsp/math.h>
#include <dsp/demodulator.h>
#include <dsp/routing.h>
#include <dsp/sink.h>
#include <dsp/vfo.h>
#include <dsp/block.h>
#include <dsp/filter.h>
#include <dsp/window.h>
#include <dsp/audio.h>
#include <io/audio.h>
#include <module.h>
#include <signal_path/signal_path.h>
#include <dsp/processing.h>
class SigPath {
public:
@ -58,13 +53,14 @@ private:
dsp::AMDemod amDemod;
dsp::SSBDemod ssbDemod;
// Gain control
dsp::AGC agc;
// Audio output
dsp::MonoToStereo m2s;
dsp::filter_window::BlackmanWindow audioWin;
dsp::PolyphaseResampler<float> audioResamp;
dsp::NullSink<float> ns;
std::string vfoName;
float sampleRate;

View File

@ -179,32 +179,30 @@ private:
while (true) {
int count = _this->audioStream->read();
if (count < 0) { break; }
for (int i = 0; i < 240; i++) {
for (int i = 0; i < count; i++) {
sampleBuf[(i * 2) + 0] = _this->audioStream->data[i].l * 0x7FFF;
sampleBuf[(i * 2) + 1] = _this->audioStream->data[i].r * 0x7FFF;
}
_this->audioStream->flush();
_this->samplesWritten += 240;
_this->writer->writeSamples(sampleBuf, 480 * sizeof(int16_t));
_this->samplesWritten += count;
_this->writer->writeSamples(sampleBuf, count * sizeof(int16_t) * 2);
}
delete[] sampleBuf;
}
static void _iqWriteWorker(RecorderModule* _this) {
dsp::complex_t* iqBuf = new dsp::complex_t[1024];
int16_t* sampleBuf = new int16_t[2048];
int16_t* sampleBuf = new int16_t[STREAM_BUFFER_SIZE];
while (true) {
int count = _this->iqStream->read();
if (count < 0) { break; }
for (int i = 0; i < 1024; i++) {
for (int i = 0; i < count; i++) {
sampleBuf[(i * 2) + 0] = _this->iqStream->data[i].q * 0x7FFF;
sampleBuf[(i * 2) + 1] = _this->iqStream->data[i].i * 0x7FFF;
}
_this->iqStream->flush();
_this->samplesWritten += 1024;
_this->writer->writeSamples(sampleBuf, 2048 * sizeof(int16_t));
_this->samplesWritten += count;
_this->writer->writeSamples(sampleBuf, count * sizeof(int16_t) * 2);
}
delete[] iqBuf;
delete[] sampleBuf;
}

View File

@ -1,43 +1,44 @@
{
"audio": {
"Radio": {
"device": "Speakers (Realtek High Definiti",
"sampleRate": 48000.0,
"volume": 0.7265625
},
"Radio 1": {
"device": "Speakers (Realtek High Definition Audio)",
"sampleRate": 48000.0,
"volume": 0.609375
},
"Radio 2": {
"device": "CABLE Input (VB-Audio Virtual Cable)",
"sampleRate": 48000.0,
"volume": 1.0
}
},
"bandPlan": "General",
"bandPlanEnabled": true,
"fftHeight": 296,
"frequency": 99000000,
"max": 0.0,
"maximized": false,
"menuOrder": [
"Source",
"Radio",
"Recorder",
"Audio",
"Scripting",
"Band Plan",
"Display"
],
"menuWidth": 300,
"min": -52.20588302612305,
"showWaterfall": true,
"source": "",
"sourceSettings": {},
"windowSize": {
"h": 1053,
"w": 959
}
{
"audio": {
"Radio": {
"device": "Speakers (Realtek High Definiti",
"sampleRate": 48000.0,
"volume": 0.4888888895511627
},
"Radio 1": {
"device": "Speakers (Realtek High Definition Audio)",
"sampleRate": 48000.0,
"volume": 0.609375
},
"Radio 2": {
"device": "CABLE Input (VB-Audio Virtual Cable)",
"sampleRate": 48000.0,
"volume": 1.0
}
},
"bandPlan": "General",
"bandPlanEnabled": true,
"defaultSink": "Audio",
"fftHeight": 296,
"frequency": 144751270,
"max": -5.14705753326416,
"maximized": true,
"menuOrder": [
"Source",
"Radio",
"Recorder",
"Audio",
"Scripting",
"Band Plan",
"Display"
],
"menuWidth": 300,
"min": -63.97058868408203,
"showWaterfall": true,
"source": "",
"sourceSettings": {},
"windowSize": {
"h": 720,
"w": 1280
}
}

View File

@ -1,6 +1,7 @@
{
"Radio": "./radio/radio.so",
"Recorder": "./recorder/recorder.so",
"Soapy": "./soapy/soapy.so",
"RTLTCPSource": "./rtl_tcp_source/rtl_tcp_source.so"
"Radio": "./radio/Release/radio.dll",
"Recorder": "./recorder/Release/recorder.dll",
"Soapy": "./soapy/Release/soapy.dll",
"RTLTCPSource": "./rtl_tcp_source/Release/rtl_tcp_source.dll",
"RX888Source": "./rx888_source/Release/rx888_source.dll"
}

View File

@ -1,5 +1,5 @@
{
"device": "HackRF One #0 901868dc282c8f8b",
"device": "Generic RTL2832U OEM :: 00000001",
"devices": {
"AirSpy HF+ [c852435de0224af7]": {
"gains": {
@ -13,9 +13,9 @@
},
"Generic RTL2832U OEM :: 00000001": {
"gains": {
"TUNER": 49.599998474121094
"TUNER": 7.244999885559082
},
"sampleRate": 2560000.0
"sampleRate": 250000.0
},
"HackRF One #0 901868dc282c8f8b": {
"gains": {

View File

@ -0,0 +1,17 @@
cmake_minimum_required(VERSION 3.13)
project(rx888_source)
if (MSVC)
set(CMAKE_CXX_FLAGS "-O2 /std:c++17")
else()
set(CMAKE_CXX_FLAGS "-O3 -std=c++17 -fpermissive")
endif (MSVC)
include_directories("src/CyAPI")
file(GLOB SRC "src/*.cpp")
file(GLOB CYAPI "src/CyAPI/*.cpp")
add_library(rx888_source SHARED ${SRC} ${CYAPI})
target_link_libraries(rx888_source PRIVATE sdrpp_core)
set_target_properties(rx888_source PROPERTIES PREFIX "")

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,602 @@
/*
## Cypress CyAPI C++ library header file (CyAPI.h)
## =======================================================
##
## Copyright Cypress Semiconductor Corporation, 2009-2012,
## All Rights Reserved
## UNPUBLISHED, LICENSED SOFTWARE.
##
## CONFIDENTIAL AND PROPRIETARY INFORMATION
## WHICH IS THE PROPERTY OF CYPRESS.
##
## Use of this file is governed
## by the license agreement included in the file
##
## <install>/license/license.rtf
##
## where <install> is the Cypress software
## install root directory path.
##
## =======================================================
*/
#ifndef CyUSBH
#define CyUSBH
#include "cyusb30_def.h"
/* Data straucture for the Vendor request and data */
typedef struct vendorCmdData
{
UCHAR *buf; /* Pointer to the data */
UCHAR opCode; /* Vendor request code */
UINT addr; /* Read/Write address */
long size; /* Size of the read/write */
bool isRead; /* Read or write */
} vendorCmdData ;
#ifndef __USB200_H__
#define __USB200_H__
#pragma pack(push,1)
typedef struct _USB_DEVICE_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
USHORT bcdUSB;
UCHAR bDeviceClass;
UCHAR bDeviceSubClass;
UCHAR bDeviceProtocol;
UCHAR bMaxPacketSize0;
USHORT idVendor;
USHORT idProduct;
USHORT bcdDevice;
UCHAR iManufacturer;
UCHAR iProduct;
UCHAR iSerialNumber;
UCHAR bNumConfigurations;
} USB_DEVICE_DESCRIPTOR, *PUSB_DEVICE_DESCRIPTOR;
typedef struct _USB_ENDPOINT_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bEndpointAddress;
UCHAR bmAttributes;
USHORT wMaxPacketSize;
UCHAR bInterval;
} USB_ENDPOINT_DESCRIPTOR, *PUSB_ENDPOINT_DESCRIPTOR;
typedef struct _USB_CONFIGURATION_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
USHORT wTotalLength;
UCHAR bNumInterfaces;
UCHAR bConfigurationValue;
UCHAR iConfiguration;
UCHAR bmAttributes;
UCHAR MaxPower;
} USB_CONFIGURATION_DESCRIPTOR, *PUSB_CONFIGURATION_DESCRIPTOR;
typedef struct _USB_INTERFACE_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bInterfaceNumber;
UCHAR bAlternateSetting;
UCHAR bNumEndpoints;
UCHAR bInterfaceClass;
UCHAR bInterfaceSubClass;
UCHAR bInterfaceProtocol;
UCHAR iInterface;
} USB_INTERFACE_DESCRIPTOR, *PUSB_INTERFACE_DESCRIPTOR;
typedef struct _USB_STRING_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
WCHAR bString[1];
} USB_STRING_DESCRIPTOR, *PUSB_STRING_DESCRIPTOR;
typedef struct _USB_COMMON_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
} USB_COMMON_DESCRIPTOR, *PUSB_COMMON_DESCRIPTOR;
#pragma pack(pop)
#endif
/*******************************************************************************/
class CCyIsoPktInfo {
public:
LONG Status;
LONG Length;
};
/*******************************************************************************/
/* {AE18AA60-7F6A-11d4-97DD-00010229B959} */
static GUID CYUSBDRV_GUID = {0xae18aa60, 0x7f6a, 0x11d4, {0x97, 0xdd, 0x0, 0x1, 0x2, 0x29, 0xb9, 0x59}};
typedef enum {TGT_DEVICE, TGT_INTFC, TGT_ENDPT, TGT_OTHER } CTL_XFER_TGT_TYPE;
typedef enum {REQ_STD, REQ_CLASS, REQ_VENDOR } CTL_XFER_REQ_TYPE;
typedef enum {DIR_TO_DEVICE, DIR_FROM_DEVICE } CTL_XFER_DIR_TYPE;
typedef enum {XMODE_BUFFERED, XMODE_DIRECT } XFER_MODE_TYPE;
const int MAX_ENDPTS = 32;
const int MAX_INTERFACES = 255;
const int USB_STRING_MAXLEN = 256;
#define BUFSIZE_UPORT 2048 //4096 - CDT 130492
typedef enum { RAM = 1, I2CE2PROM, SPIFLASH } FX3_FWDWNLOAD_MEDIA_TYPE ;
typedef enum { SUCCESS = 0, FAILED, INVALID_MEDIA_TYPE, INVALID_FWSIGNATURE, DEVICE_CREATE_FAILED, INCORRECT_IMAGE_LENGTH, INVALID_FILE, SPILASH_ERASE_FAILED, CORRUPT_FIRMWARE_IMAGE_FILE,I2CE2PROM_UNKNOWN_I2C_SIZE } FX3_FWDWNLOAD_ERROR_CODE;
#define CYWB_BL_4_BYTES_COPY(destination,source) {memcpy((void *)(destination), (void *)(source), 4);}
/********************************************************************************
*
* The CCyEndPoint ABSTRACT Class
*
********************************************************************************/
class CCyUSBEndPoint
{
protected:
bool WaitForIO(OVERLAPPED *ovLapStatus);
virtual PUCHAR BeginDirectXfer(PUCHAR buf, LONG bufLen, OVERLAPPED *ov);
virtual PUCHAR BeginBufferedXfer(PUCHAR buf, LONG bufLen, OVERLAPPED *ov);
public:
CCyUSBEndPoint(void);
CCyUSBEndPoint(CCyUSBEndPoint& ept);
CCyUSBEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor);
CCyUSBEndPoint(HANDLE hDev, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor,USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR* SSEndPtDescriptor);
HANDLE hDevice;
/* The fields of an EndPoint Descriptor */
UCHAR DscLen;
UCHAR DscType;
UCHAR Address;
UCHAR Attributes;
USHORT MaxPktSize;
USHORT PktsPerFrame;
UCHAR Interval;
/* This are the fields for Super speed endpoint */
UCHAR ssdscLen;
UCHAR ssdscType;
UCHAR ssmaxburst; /* Maximum number of packets endpoint can send in one burst */
UCHAR ssbmAttribute; /* store endpoint attribute like for bulk it will be number of streams */
USHORT ssbytesperinterval;
/* Other fields */
ULONG TimeOut;
ULONG UsbdStatus;
ULONG NtStatus;
DWORD bytesWritten;
DWORD LastError;
bool bIn;
XFER_MODE_TYPE XferMode;
bool XferData(PUCHAR buf, LONG &len, CCyIsoPktInfo* pktInfos = NULL);
bool XferData(PUCHAR buf, LONG &bufLen, CCyIsoPktInfo* pktInfos, bool pktMode);
virtual PUCHAR BeginDataXfer(PUCHAR buf, LONG len, OVERLAPPED *ov) = 0;
virtual bool FinishDataXfer(PUCHAR buf, LONG &len, OVERLAPPED *ov, PUCHAR pXmitBuf, CCyIsoPktInfo* pktInfos = NULL);
bool WaitForXfer(OVERLAPPED *ov, ULONG tOut);
ULONG GetXferSize(void);
void SetXferSize(ULONG xfer);
bool Reset(void);
bool Abort(void);
};
/********************************************************************************
*
* The Control Endpoint Class
*
********************************************************************************/
class CCyControlEndPoint : public CCyUSBEndPoint
{
public:
CCyControlEndPoint(void);
CCyControlEndPoint(CCyControlEndPoint& ept);
CCyControlEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor);
CTL_XFER_TGT_TYPE Target;
CTL_XFER_REQ_TYPE ReqType;
CTL_XFER_DIR_TYPE Direction;
UCHAR ReqCode;
WORD Value;
WORD Index;
bool Read(PUCHAR buf, LONG &len);
bool Write(PUCHAR buf, LONG &len);
PUCHAR BeginDataXfer(PUCHAR buf, LONG len, OVERLAPPED *ov);
};
/********************************************************************************
*
* The Isoc Endpoint Class
*
********************************************************************************/
class CCyIsocEndPoint : public CCyUSBEndPoint
{
protected:
virtual PUCHAR BeginDirectXfer(PUCHAR buf, LONG bufLen, OVERLAPPED *ov);
virtual PUCHAR BeginBufferedXfer(PUCHAR buf, LONG bufLen, OVERLAPPED *ov);
public:
CCyIsocEndPoint(void);
CCyIsocEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor);
CCyIsocEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor,USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR* SSEndPtDescriptor);
PUCHAR BeginDataXfer(PUCHAR buf, LONG len, OVERLAPPED *ov);
CCyIsoPktInfo* CreatePktInfos(LONG bufLen, int &packets);
};
/********************************************************************************
*
* The Bulk Endpoint Class
*
********************************************************************************/
class CCyBulkEndPoint : public CCyUSBEndPoint
{
public:
CCyBulkEndPoint(void);
CCyBulkEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor);
CCyBulkEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor,USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR* SSEndPtDescriptor);
PUCHAR BeginDataXfer(PUCHAR buf, LONG len, OVERLAPPED *ov);
};
/********************************************************************************
*
* The Interrupt Endpoint Class
*
********************************************************************************/
class CCyInterruptEndPoint : public CCyUSBEndPoint
{
public:
CCyInterruptEndPoint(void);
CCyInterruptEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor);
CCyInterruptEndPoint(HANDLE h, PUSB_ENDPOINT_DESCRIPTOR pEndPtDescriptor,USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR* SSEndPtDescriptor);
PUCHAR BeginDataXfer(PUCHAR buf, LONG len, OVERLAPPED *ov);
};
/********************************************************************************
*
* The Interface Class
*
********************************************************************************/
class CCyUSBInterface
{
public:
CCyUSBEndPoint *EndPoints[MAX_ENDPTS]; /* Holds pointers to all the interface's endpoints,
plus a pointer to the Control endpoint zero */
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bInterfaceNumber;
UCHAR bAlternateSetting;
UCHAR bNumEndpoints; /* Not counting the control endpoint */
UCHAR bInterfaceClass;
UCHAR bInterfaceSubClass;
UCHAR bInterfaceProtocol;
UCHAR iInterface;
UCHAR bAltSettings;
USHORT wTotalLength; /* Needed in case Intfc has additional (non-endpt) descriptors */
CCyUSBInterface(HANDLE handle, PUSB_INTERFACE_DESCRIPTOR pIntfcDescriptor,UCHAR usb30Dummy);
CCyUSBInterface(HANDLE h, PUSB_INTERFACE_DESCRIPTOR pIntfcDescriptor);
CCyUSBInterface(CCyUSBInterface& ifc); /* Copy Constructor */
~CCyUSBInterface(void);
};
/********************************************************************************
*
* The Config Class
*
********************************************************************************/
class CCyUSBConfig
{
public:
CCyUSBInterface *Interfaces[MAX_INTERFACES];
UCHAR bLength;
UCHAR bDescriptorType;
USHORT wTotalLength;
UCHAR bNumInterfaces;
UCHAR bConfigurationValue;
UCHAR iConfiguration;
UCHAR bmAttributes;
UCHAR MaxPower;
UCHAR AltInterfaces;
CCyUSBConfig(void);
CCyUSBConfig(CCyUSBConfig& cfg); /* Copy Constructor */
CCyUSBConfig(HANDLE h, PUSB_CONFIGURATION_DESCRIPTOR pConfigDescr);
CCyUSBConfig(HANDLE h, PUSB_CONFIGURATION_DESCRIPTOR pConfigDescr,UCHAR usb30Dummy);
~CCyUSBConfig(void);
};
/********************************************************************************
*
* The Bos USB20 Extesnion Class
*
********************************************************************************/
class CCyBosUSB20Extesnion
{
public:
UCHAR bLength; /* Descriptor length */
UCHAR bDescriptorType; /* Descriptor Type */
UCHAR bDevCapabilityType; /* Device capability type */
UINT bmAttribute; /* Bitmap encoding for supprted feature and Link power managment supprted if set */
CCyBosUSB20Extesnion(void);
CCyBosUSB20Extesnion(HANDLE h,PUSB_BOS_USB20_DEVICE_EXTENSION BosUsb20ExtDesc);
};
/********************************************************************************
*
* The Bos SuperSpeed Capability Class
*
********************************************************************************/
class CCyBosSuperSpeedCapability
{
public:
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bDevCapabilityType;
UCHAR bmAttribute;
USHORT SpeedsSuported;
UCHAR bFunctionalitySupporte;
UCHAR bU1DevExitLat;
USHORT bU2DevExitLat;
CCyBosSuperSpeedCapability(void);
CCyBosSuperSpeedCapability(HANDLE h,PUSB_BOS_SS_DEVICE_CAPABILITY pUSB_SuperSpeedUsb);
};
/********************************************************************************
*
* The Bos Container ID Class
*
********************************************************************************/
class CCyBosContainerID
{
public:
UCHAR bLength; /* Descriptor length */
UCHAR bDescriptorType; /* Descriptor Type */
UCHAR bDevCapabilityType; /* Device capability type */
UCHAR bReserved; /* no use */
UCHAR ContainerID[USB_BOS_CAPABILITY_TYPE_CONTAINER_ID_SIZE]; /* UUID */
CCyBosContainerID(void);
CCyBosContainerID(HANDLE h,PUSB_BOS_CONTAINER_ID pContainerID);
};
/********************************************************************************
*
* The USB BOS Class
*
********************************************************************************/
class CCyUSBBOS
{
public:
CCyBosContainerID *pContainer_ID;
CCyBosUSB20Extesnion *pUSB20_DeviceExt;
CCyBosSuperSpeedCapability *pSS_DeviceCap;
UCHAR bLength; /* Descriptor length */
UCHAR bDescriptorType; /* Descriptor Type */
USHORT wTotalLength; /* Total length of descriptor ( icluding device capabilty */
UCHAR bNumDeviceCaps; /* Number of device capability descriptors in BOS */
CCyUSBBOS(void);
CCyUSBBOS(HANDLE h,PUSB_BOS_DESCRIPTOR pBosDescrData);
~CCyUSBBOS();
};
/*********************************************************************************
*
* The USB Device Class - This is the main class that contains members of all the
* other classes.
*
* To use the library, create an instance of this Class and call it's Open method.
*
*********************************************************************************/
class CCyUSBDevice
{
/* The public members are accessible (i.e. corruptible) by the user of the library
* Algorithms of the class don't rely on any public members. Instead, they use the
* private members of the class for their calculations. */
public:
CCyUSBDevice(HANDLE hnd = NULL, GUID guid = CYUSBDRV_GUID, BOOL bOpen = true);
~CCyUSBDevice(void);
CCyUSBEndPoint **EndPoints; /* Shortcut to USBCfgs[CfgNum]->Interfaces[IntfcIndex]->Endpoints */
CCyUSBEndPoint *EndPointOf(UCHAR addr);
CCyUSBBOS *UsbBos;
CCyIsocEndPoint *IsocInEndPt;
CCyIsocEndPoint *IsocOutEndPt;
CCyBulkEndPoint *BulkInEndPt;
CCyBulkEndPoint *BulkOutEndPt;
CCyControlEndPoint *ControlEndPt;
CCyInterruptEndPoint *InterruptInEndPt;
CCyInterruptEndPoint *InterruptOutEndPt;
USHORT StrLangID;
ULONG LastError;
ULONG UsbdStatus;
ULONG NtStatus;
ULONG DriverVersion;
ULONG USBDIVersion;
char DeviceName[USB_STRING_MAXLEN];
char FriendlyName[USB_STRING_MAXLEN];
wchar_t Manufacturer[USB_STRING_MAXLEN];
wchar_t Product[USB_STRING_MAXLEN];
wchar_t SerialNumber[USB_STRING_MAXLEN];
CHAR DevPath[USB_STRING_MAXLEN];
USHORT BcdUSB;
USHORT VendorID;
USHORT ProductID;
UCHAR USBAddress;
UCHAR DevClass;
UCHAR DevSubClass;
UCHAR DevProtocol;
INT MaxPacketSize;
USHORT BcdDevice;
UCHAR ConfigValue;
UCHAR ConfigAttrib;
UCHAR MaxPower;
UCHAR IntfcClass;
UCHAR IntfcSubClass;
UCHAR IntfcProtocol;
bool bHighSpeed;
bool bSuperSpeed;
DWORD BytesXfered;
UCHAR DeviceCount(void);
UCHAR ConfigCount(void);
UCHAR IntfcCount(void);
UCHAR AltIntfcCount(void);
UCHAR EndPointCount(void);
void SetConfig(UCHAR cfg);
UCHAR Config(void) { return CfgNum; } /* Normally 0 */
UCHAR Interface(void) { return IntfcNum; } /* Usually 0 */
/* No SetInterface method since only 1 intfc per device (per Windows) */
UCHAR AltIntfc(void);
bool SetAltIntfc(UCHAR alt);
GUID DriverGUID(void) { return DrvGuid; }
HANDLE DeviceHandle(void) { return hDevice; }
void UsbdStatusString(ULONG stat, PCHAR s);
bool CreateHandle(UCHAR dev);
void DestroyHandle();
bool Open(UCHAR dev);
void Close(void);
bool Reset(void);
bool ReConnect(void);
bool Suspend(void);
bool Resume(void);
bool IsOpen(void) { return (hDevice != INVALID_HANDLE_VALUE); }
UCHAR PowerState(void);
bool GetBosDescriptor(PUSB_BOS_DESCRIPTOR descr);
bool GetBosUSB20DeviceExtensionDescriptor(PUSB_BOS_USB20_DEVICE_EXTENSION descr);
bool GetBosContainedIDDescriptor(PUSB_BOS_CONTAINER_ID descr);
bool GetBosSSCapabilityDescriptor(PUSB_BOS_SS_DEVICE_CAPABILITY descr);
void GetDeviceDescriptor(PUSB_DEVICE_DESCRIPTOR descr);
void GetConfigDescriptor(PUSB_CONFIGURATION_DESCRIPTOR descr);
void GetIntfcDescriptor(PUSB_INTERFACE_DESCRIPTOR descr);
CCyUSBConfig GetUSBConfig(int index);
private:
USB_DEVICE_DESCRIPTOR USBDeviceDescriptor;
PUSB_CONFIGURATION_DESCRIPTOR USBConfigDescriptors[2];
PUSB_BOS_DESCRIPTOR pUsbBosDescriptor;
CCyUSBConfig *USBCfgs[2];
HANDLE hWnd;
HANDLE hDevice;
HANDLE hDevNotification;
HANDLE hHndNotification;
GUID DrvGuid;
UCHAR Devices;
UCHAR Interfaces;
UCHAR AltInterfaces;
UCHAR Configs;
UCHAR DevNum;
UCHAR CfgNum;
UCHAR IntfcNum; /* The current selected interface's bInterfaceNumber */
UCHAR IntfcIndex; /* The entry in the Config's interfaces table matching to IntfcNum and AltSetting */
bool GetInternalBosDescriptor();
void GetDevDescriptor(void);
void GetCfgDescriptor(int descIndex);
void GetString(wchar_t *s, UCHAR sIndex);
void SetStringDescrLanguage(void);
void SetAltIntfcParams(UCHAR alt);
bool IoControl(ULONG cmd, PUCHAR buf, ULONG len);
void SetEndPointPtrs(void);
void GetDeviceName(void);
void GetFriendlyName(void);
void GetDriverVer(void);
void GetUSBDIVer(void);
void GetSpeed(void);
void GetUSBAddress(void);
//void CloseEndPtHandles(void);
bool RegisterForPnpEvents(HANDLE h);
};
/********************************************************************************
*
* The FX3 Device Class
*
********************************************************************************/
class CCyFX3Device: public CCyUSBDevice
{
public:
CCyFX3Device(void);
~CCyFX3Device(void);
bool IsBootLoaderRunning();
FX3_FWDWNLOAD_ERROR_CODE DownloadFw(char *fileName, FX3_FWDWNLOAD_MEDIA_TYPE enMediaType);
private:
bool Ep0VendorCommand(vendorCmdData cmdData);
bool SetProgramEntry(UCHAR opCode,UINT start_addr);
bool DownloadBufferToDevice(UINT start_addr, USHORT count, UCHAR *data_buf, UCHAR opCode);
bool UploadBufferFromDevice(UINT start_addr, USHORT count, UCHAR *data_buf, UCHAR opCode);
FX3_FWDWNLOAD_ERROR_CODE DownloadFwToRam(PUCHAR buffer_p, UINT fw_size, UCHAR opCode);
FX3_FWDWNLOAD_ERROR_CODE DownloadUserIMGtoI2CE2PROM(PUCHAR buffer_p, UINT fw_size, UCHAR opCode);
FX3_FWDWNLOAD_ERROR_CODE DownloadUserIMGtoSPIFLASH(PUCHAR buffer_p, UINT fw_size, UCHAR opCode);
FX3_FWDWNLOAD_ERROR_CODE EraseSectorOfSPIFlash(UINT SectorNumber, UCHAR opCode);
bool WriteToSPIFlash(PUCHAR Buf, UINT buflen, UINT ByteAddress, UCHAR opCode);
};
/********************************************************************************/
#endif

View File

@ -0,0 +1,90 @@
/*
## Cypress CyAPI C++ library USB3.0 defination header file (CyUSB30_def.h)
## =======================================================
##
## Copyright Cypress Semiconductor Corporation, 2009-2012,
## All Rights Reserved
## UNPUBLISHED, LICENSED SOFTWARE.
##
## CONFIDENTIAL AND PROPRIETARY INFORMATION
## WHICH IS THE PROPERTY OF CYPRESS.
##
## Use of this file is governed
## by the license agreement included in the file
##
## <install>/license/license.rtf
##
## where <install> is the Cypress software
## install root directory path.
##
## =======================================================
*/
#ifndef _CYUSB30_H
#define _CYUSB30_H
//#pragma pack(1)
#pragma pack(push, 1)
// USB3.0 specific constant defination
#define BCDUSBJJMASK 0xFF00 //(0xJJMN JJ - Major version,M Minor version, N sub-minor vesion)
#define USB30MAJORVER 0x0300
#define USB20MAJORVER 0x0200
#define USB_BOS_DESCRIPTOR_TYPE 0x0F
#define USB_DEVICE_CAPABILITY 0x10
#define USB_SUPERSPEED_ENDPOINT_COMPANION 0x30
#define USB_BOS_CAPABILITY_TYPE_Wireless_USB 0x01
#define USB_BOS_CAPABILITY_TYPE_USB20_EXT 0x02
#define USB_BOS_CAPABILITY_TYPE_SUPERSPEED_USB 0x03
#define USB_BOS_CAPABILITY_TYPE_CONTAINER_ID 0x04
#define USB_BOS_CAPABILITY_TYPE_CONTAINER_ID_SIZE 0x10
#define USB_BOS_DEVICE_CAPABILITY_TYPE_INDEX 0x2
//constant defination
typedef struct _USB_BOS_DESCRIPTOR
{
UCHAR bLength;/* Descriptor length*/
UCHAR bDescriptorType;/* Descriptor Type */
USHORT wTotalLength;/* Total length of descriptor ( icluding device capability*/
UCHAR bNumDeviceCaps;/* Number of device capability descriptors in BOS */
}USB_BOS_DESCRIPTOR,*PUSB_BOS_DESCRIPTOR;
typedef struct _USB_BOS_USB20_DEVICE_EXTENSION
{
UCHAR bLength;/* Descriptor length*/
UCHAR bDescriptorType;/* Descriptor Type */
UCHAR bDevCapabilityType;/* Device capability type*/
UINT bmAttribute;// Bitmap encoding for supprted feature and Link power managment supprted if set
}USB_BOS_USB20_DEVICE_EXTENSION,*PUSB_BOS_USB20_DEVICE_EXTENSION;
typedef struct _USB_BOS_SS_DEVICE_CAPABILITY
{
UCHAR bLength;/* Descriptor length*/
UCHAR bDescriptorType;/* Descriptor Type */
UCHAR bDevCapabilityType;/* Device capability type*/
UCHAR bmAttribute;// Bitmap encoding for supprted feature and Link power managment supprted if set
USHORT wSpeedsSuported;//low speed supported if set,full speed supported if set,high speed supported if set,super speed supported if set,15:4 nt used
UCHAR bFunctionalitySupporte;
UCHAR bU1DevExitLat;//U1 device exit latency
USHORT bU2DevExitLat;//U2 device exit latency
}USB_BOS_SS_DEVICE_CAPABILITY,*PUSB_BOS_SS_DEVICE_CAPABILITY;
typedef struct _USB_BOS_CONTAINER_ID
{
UCHAR bLength;/* Descriptor length*/
UCHAR bDescriptorType;/* Descriptor Type */
UCHAR bDevCapabilityType;/* Device capability type*/
UCHAR bReserved; // no use
UCHAR ContainerID[USB_BOS_CAPABILITY_TYPE_CONTAINER_ID_SIZE];/* UUID */
}USB_BOS_CONTAINER_ID,*PUSB_BOS_CONTAINER_ID;
typedef struct _USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR
{
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bMaxBurst;
UCHAR bmAttributes;
USHORT bBytesPerInterval;
}USB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR,*PUSB_SUPERSPEED_ENDPOINT_COMPANION_DESCRIPTOR;
#pragma pack(pop)
#endif /*_CYUSB30_H*/

View File

@ -0,0 +1,256 @@
#include "Si5351.h"
#include "openFX3.h"
#include <spdlog/spdlog.h>
#define DbgPrintf spdlog::info
#define SI_CLK0_CONTROL 16 // Registers
#define SI_CLK1_CONTROL 17
#define SI_CLK2_CONTROL 18
#define SI_SYNTH_PLL_A 26
#define SI_SYNTH_PLL_B 34
#define SI_SYNTH_MS_0 42
#define SI_SYNTH_MS_1 50
#define SI_SYNTH_MS_2 58
#define SI_PLL_RESET (0x177)
#define SI_R_DIV_1 (0) // 0b00000000 /
#define SI_R_DIV_2 (0x10) // 0b00010000
#define SI_R_DIV_4 (0x20) // 0b00100000
#define SI_R_DIV_8 (0x30) // 0b00110000
#define SI_R_DIV_16 (0x40) // 0b01000000
#define SI_R_DIV_32 (0x50) // 0b01010000
#define SI_R_DIV_64 (0x60) // 0b01100000
#define SI_R_DIV_128 (0x70) // 0b01110000
#define SI_CLK_SRC_PLL_A 0b00000000
#define SI_CLK_SRC_PLL_B 0b00100000
#define SI5351_FREQ 27000000 // Crystal frequency
#define SI5351_PLL_FIXED 80000000000ULL
#define SI5351_ADDR (0x60 << 1 )
#define SI5351_CRYSTAL_LOAD 183
#define SI5351_CRYSTAL_LOAD_MASK (3<<6)
#define SI5351_CRYSTAL_LOAD_0PF (0<<6)
#define SI5351_CRYSTAL_LOAD_6PF (1<<6)
#define SI5351_CRYSTAL_LOAD_8PF (2<<6)
#define SI5351_CRYSTAL_LOAD_10PF (3<<6)
#define SI5351_PLL_INPUT_SOURCE 15
#define SI5351_CLKIN_DIV_MASK (3<<6)
#define SI5351_CLKIN_DIV_1 (0<<6)
#define SI5351_CLKIN_DIV_2 (1<<6)
#define SI5351_CLKIN_DIV_4 (2<<6)
#define SI5351_CLKIN_DIV_8 (3<<6)
#define SI5351_PLLB_SOURCE (1<<3)
#define SI5351_PLLA_SOURCE (1<<2)
void Si5351init()
{
// Set crystal load capacitance
fx3SendI2cbyte(SI5351_ADDR, SI5351_CRYSTAL_LOAD, SI5351_CRYSTAL_LOAD_6PF | 0b00010010);
fx3SendI2cbyte(SI5351_ADDR, SI_CLK0_CONTROL, 0x80); // clocks off
fx3SendI2cbyte(SI5351_ADDR, SI_CLK1_CONTROL, 0x80);
fx3SendI2cbyte(SI5351_ADDR, SI_CLK2_CONTROL, 0x80);
// si5351aSetFrequency(ADC_FREQ, R820T_ZERO);
DbgPrintf("Si5351_init()\n");
}
#define _PLLDEBUG_
//
// Set up specified PLL with mult, num and denom
// mult is 15..90
// num is 0..1,048,575 (0xFFFFF)
// denom is 0..1,048,575 (0xFFFFF)
//
static void setupPLL(UINT8 pll, UINT8 mult, UINT32 num, UINT32 denom)
{
UINT32 P1; // PLL config register P1
UINT32 P2; // PLL config register P2
UINT32 P3; // PLL config register P3
UINT8 data[8];
// the actual multiplier is mult + num / denom
#ifdef _PLLDEBUG_
double fa;
double x = 27000000.0;
fa = x * ((double)mult + (double)num / (double)denom);
DbgPrintf((char *) "pll = %d , mult = %d , num = %d , denom = %d\n", pll, mult, num, denom);
DbgPrintf((char *) "pll target %e \n", fa);
#endif
P1 = (UINT32)(128 * ((float)num / (float)denom));
P1 = (UINT32)(128 * (UINT32)(mult)+P1 - 512);
P2 = (UINT32)(128 * ((float)num / (float)denom));
P2 = (UINT32)(128 * num - denom * P2);
P3 = denom;
data[0] = (P3 & 0x0000FF00) >> 8;
data[1] = (P3 & 0x000000FF);
data[2] = (P1 & 0x00030000) >> 16;
data[3] = (P1 & 0x0000FF00) >> 8;
data[4] = (P1 & 0x000000FF);
data[5] = ((P3 & 0x000F0000) >> 12) | ((P2 & 0x000F0000) >> 16);
data[6] = (P2 & 0x0000FF00) >> 8;
data[7] = (P2 & 0x000000FF);
fx3SendI2cbytes(SI5351_ADDR, pll, data, sizeof(data));
}
//
// Set up MultiSynth with integer divider and R divider
// R divider is the bit value which is OR'ed onto the appropriate register, it is a #define in si5351a.h
//
static void setupMultisynth(UINT8 synth, UINT32 divider, UINT8 rDiv)
{
UINT32 P1; // Synth config register P1
UINT32 P2; // Synth config register P2
UINT32 P3; // Synth config register P3
UINT8 data[8];
#ifdef _PLLDEBUG_
DbgPrintf("setupMultisynth synth = %d divider = %d rDiv= %d \n", synth, divider, rDiv);
//DbgPrintf("output expected f = %e\n", fa / divider);
#endif
P1 = 128 * divider - 512;
P2 = 0; // P2 = 0, P3 = 1 forces an integer value for the divider
P3 = 1;
data[0] = (P3 & 0x0000FF00) >> 8;
data[1] = (P3 & 0x000000FF);
data[2] = ((P1 & 0x00030000) >> 16) | rDiv;
data[3] = (P1 & 0x0000FF00) >> 8;
data[4] = (P1 & 0x000000FF);
data[5] = ((P3 & 0x000F0000) >> 12) | ((P2 & 0x000F0000) >> 16);
data[6] = (P2 & 0x0000FF00) >> 8;
data[7] = (P2 & 0x000000FF);
fx3SendI2cbytes(SI5351_ADDR, synth, data, sizeof(data));
}
//
// Switches off Si5351a output
// Example: si5351aOutputOff(SI_CLK0_CONTROL);
// will switch off output CLK0
//
void si5351aOutputOff(UINT8 clk)
{
fx3SendI2cbyte(SI5351_ADDR, clk, 0x80); // Refer to SiLabs AN619 to see bit values - 0x80 turns off the output stage
}
void si5351aSetFrequency(UINT32 freq, UINT32 freq2)
{
UINT32 frequency;
UINT32 pllFreq;
UINT32 xtalFreq = SI5351_FREQ;
UINT32 l;
double f;
UINT8 mult;
UINT32 num;
UINT32 denom;
UINT32 divider;
UINT32 rdiv;
double corr = 0.9999314;
//double corr = 1.0;
DbgPrintf("BBRF103 si5351 SetFreq ADC sampling:%d R820T reference:%d\n", freq, freq2);
rdiv = (UINT32)SI_R_DIV_1;
frequency = (UINT32)((double)freq * corr);
while (frequency < 1000000)
{
frequency = frequency * 2;
rdiv += SI_R_DIV_2;
}
#ifdef _PLLDEBUG_
DbgPrintf((char *) "\nCLK0 frequency %d \n", frequency);
#endif
divider = 900000000UL / frequency;// Calculate the division ratio. 900,000,000 is the maximum internal
// PLL frequency: 900MHz
if (divider % 2) divider--; // Ensure an even integer division ratio
pllFreq = divider * frequency; // Calculate the pllFrequency: the divider * desired output frequency
#ifdef _PLLDEBUG_
DbgPrintf((char *) "pllA Freq %d \n", pllFreq);
#endif
mult = pllFreq / xtalFreq; // Determine the multiplier to get to the required pllFrequency
l = pllFreq % xtalFreq; // It has three parts:
f = (double)l; // mult is an integer that must be in the range 15..90
f *= 1048575; // num and denom are the fractional parts, the numerator and denominator
f /= xtalFreq; // each is 20 bits (range 0..1048575)
num = (UINT32)f; // the actual multiplier is mult + num / denom
denom = 1048575; // For simplicity we set the denominator to the maximum 1048575
// Set up PLL A with the calculated multiplication ratio
setupPLL(SI_SYNTH_PLL_A, mult, num, denom);
// Set up MultiSynth divider 0, with the calculated divider.
// The final R division stage can divide by a power of two, from 1..128.
// represented by constants SI_R_DIV1 to SI_R_DIV128 (see si5351a.h header file)
// If you want to output frequencies below 1MHz, you have to use the
// final R division stage
setupMultisynth(SI_SYNTH_MS_0, divider, rdiv);
// Reset the PLL. This causes a glitch in the output. For small changes to
// the parameters, you don't need to reset the PLL, and there is no glitch
fx3SendI2cbyte((UINT8)SI5351_ADDR, (UINT8)SI_PLL_RESET, (UINT8)0x20); //pllA
// Finally switch on the CLK0 output (0x4F)
// and set the MultiSynth0 input to be PLL A
fx3SendI2cbyte(SI5351_ADDR, SI_CLK0_CONTROL, 0x4F | SI_CLK_SRC_PLL_A);
if (freq2 > 0)
{
// calculate clk2
frequency = (UINT32)((double)freq2 * corr);
rdiv = SI_R_DIV_1;
xtalFreq = SI5351_FREQ;
while (frequency <= 1000000)
{
frequency = frequency * 2;
rdiv += SI_R_DIV_2;
}
#ifdef _PLLDEBUG_
DbgPrintf((char *) "\nCLK2 frequency %d \n", frequency);
#endif
divider = 900000000UL / frequency;// Calculate the division ratio. 900,000,000 is the maximum internal
// PLL frequency: 900MHz
if (divider % 2) divider--; // Ensure an even integer division ratio
pllFreq = divider * frequency; // Calculate the pllFrequency: the divider * desired output frequency
#ifdef _PLLDEBUG_
DbgPrintf((char *) "pllB Freq %d \n", pllFreq);
#endif
mult = pllFreq / xtalFreq; // Determine the multiplier to get to the required pllFrequency
l = pllFreq % xtalFreq; // It has three parts:
f = (double)l; // mult is an integer that must be in the range 15..90
f *= 1048575; // num and denom are the fractional parts, the numerator and denominator
f /= xtalFreq; // each is 20 bits (range 0..1048575)
num = (UINT32)f; // the actual multiplier is mult + num / denom
denom = 1048575; // For simplicity we set the denominator to the maximum 1048575
// Set up PLL B with the calculated multiplication ratio
setupPLL(SI_SYNTH_PLL_B, mult, num, denom);
// Set up MultiSynth divider 0, with the calculated divider.
// The final R division stage can divide by a power of two, from 1..128.
// represented by constants SI_R_DIV1 to SI_R_DIV128 (see si5351a.h header file)
// If you want to output frequencies below 1MHz, you have to use the
// final R division stage
setupMultisynth(SI_SYNTH_MS_2, divider, rdiv);
// Reset the PLL. This causes a glitch in the output. For small changes to
// the parameters, you don't need to reset the PLL, and there is no glitch
fx3SendI2cbyte((UINT8)SI5351_ADDR, (UINT8)SI_PLL_RESET, (UINT8)0x80); //pllB
// Finally switch on the CLK2 output (0x4C)
// and set the MultiSynth0 input to be PLL A
fx3SendI2cbyte(SI5351_ADDR, SI_CLK2_CONTROL, 0x4C | SI_CLK_SRC_PLL_B); // select PLLB
// calculate clk2
}
else
{
fx3SendI2cbyte(SI5351_ADDR, SI_CLK2_CONTROL, 0x80);
}
}

View File

@ -0,0 +1,13 @@
// MIT License Copyright (c) 2017 ik1xpv@gmail.com, http://www.steila.com/blog
#ifndef SI5351_H
#define SI5351_H
#include <basetsd.h>
void Si5351init();
void si5351aSetFrequency(UINT32 freq, UINT32 freq2);
void si5351aOutputOff(UINT8 clk);
#endif

View File

@ -0,0 +1,46 @@
// Note: see usbdi.h in the DDK for the USBD_STATUS source definitions
typedef LONG USBD_STATUS;
#define USBD_STATUS(Status) ((ULONG)(Status) & 0x0FFFFFFFL)
#define USBD_STATE(Status) ((ULONG)(Status) & 0xF0000000L)
// HC status codes (Note: both error and stall bit are set)
#define USBD_STATUS_SUCCESS ((USBD_STATUS)0x00000000L)
#define USBD_STATUS_PENDING ((USBD_STATUS)0x40000000L)
#define USBD_STATUS_HALTED ((USBD_STATUS)0xC0000000L)
#define USBD_STATUS_ERROR ((USBD_STATUS)0x80000000L)
#define USBD_STATUS_CRC ((USBD_STATUS)0xC0000001L)
#define USBD_STATUS_BTSTUFF ((USBD_STATUS)0xC0000002L)
#define USBD_STATUS_DATA_TOGGLE_MISMATCH ((USBD_STATUS)0xC0000003L)
#define USBD_STATUS_STALL_PID ((USBD_STATUS)0xC0000004L)
#define USBD_STATUS_DEV_NOT_RESPONDING ((USBD_STATUS)0xC0000005L)
#define USBD_STATUS_PID_CHECK_FAILURE ((USBD_STATUS)0xC0000006L)
#define USBD_STATUS_UNEXPECTED_PID ((USBD_STATUS)0xC0000007L)
#define USBD_STATUS_DATA_OVERRUN ((USBD_STATUS)0xC0000008L)
#define USBD_STATUS_DATA_UNDERRUN ((USBD_STATUS)0xC0000009L)
#define USBD_STATUS_RESERVED1 ((USBD_STATUS)0xC000000AL)
#define USBD_STATUS_RESERVED2 ((USBD_STATUS)0xC000000BL)
#define USBD_STATUS_BUFFER_OVERRUN ((USBD_STATUS)0xC000000CL)
#define USBD_STATUS_BUFFER_UNDERRUN ((USBD_STATUS)0xC000000DL)
#define USBD_STATUS_NOT_ACCESSED ((USBD_STATUS)0xC000000FL)
#define USBD_STATUS_FIFO ((USBD_STATUS)0xC0000010L)
#define USBD_STATUS_ENDPOINT_HALTED ((USBD_STATUS)0xC0000030L)
#define USBD_STATUS_NO_MEMORY ((USBD_STATUS)0x80000100L)
#define USBD_STATUS_INVALID_URB_FUNCTION ((USBD_STATUS)0x80000200L)
#define USBD_STATUS_INVALID_PARAMETER ((USBD_STATUS)0x80000300L)
#define USBD_STATUS_ERROR_BUSY ((USBD_STATUS)0x80000400L)
#define USBD_STATUS_REQUEST_FAILED ((USBD_STATUS)0x80000500L)
#define USBD_STATUS_INVALID_PIPE_HANDLE ((USBD_STATUS)0x80000600L)
#define USBD_STATUS_NO_BANDWIDTH ((USBD_STATUS)0x80000700L)
#define USBD_STATUS_INTERNAL_HC_ERROR ((USBD_STATUS)0x80000800L)
#define USBD_STATUS_ERROR_SHORT_TRANSFER ((USBD_STATUS)0x80000900L)
#define USBD_STATUS_BAD_START_FRAME ((USBD_STATUS)0xC0000A00L)
#define USBD_STATUS_ISOCH_REQUEST_FAILED ((USBD_STATUS)0xC0000B00L)
#define USBD_STATUS_FRAME_CONTROL_OWNED ((USBD_STATUS)0xC0000C00L)
#define USBD_STATUS_FRAME_CONTROL_NOT_OWNED ((USBD_STATUS)0xC0000D00L)
#define USBD_STATUS_CANCELED ((USBD_STATUS)0x00010000L)
#define USBD_STATUS_CANCELING ((USBD_STATUS)0x00020000L)

View File

@ -0,0 +1,26 @@
/*
## Cypress CyAPI C++ library version number header file (VersionNo.h)
## =======================================================
##
## Copyright Cypress Semiconductor Corporation, 2009-2012,
## All Rights Reserved
## UNPUBLISHED, LICENSED SOFTWARE.
##
## CONFIDENTIAL AND PROPRIETARY INFORMATION
## WHICH IS THE PROPERTY OF CYPRESS.
##
## Use of this file is governed
## by the license agreement included in the file
##
## <install>/license/license.rtf
##
## where <install> is the Cypress software
## install root directory path.
##
## =======================================================
*/
#define FILEVER 1,2,1,0
#define PRODUCTVER 1,2,1,0
#define STRFILEVER "1, 2, 1, 0"
#define STRPRODUCTVER "1, 2, 1, 0"
#define STRFILEVER_ASSENBLY "1.2.1.0"

View File

@ -0,0 +1,213 @@
/*
## Cypress CyAPI C++ library IOCTL defination header file (cyioctl.h)
## =======================================================
##
## Copyright Cypress Semiconductor Corporation, 2009-2012,
## All Rights Reserved
## UNPUBLISHED, LICENSED SOFTWARE.
##
## CONFIDENTIAL AND PROPRIETARY INFORMATION
## WHICH IS THE PROPERTY OF CYPRESS.
##
## Use of this file is governed
## by the license agreement included in the file
##
## <install>/license/license.rtf
##
## where <install> is the Cypress software
## install root directory path.
##
## =======================================================
*/
#ifndef __IOCTL_H__
#define __IOCTL_H__
#ifndef DRIVER
#ifndef CTL_CODE
#include "devioctl.h"
#endif
#ifndef BM_REQUEST_TYPE
#include "usb200.h"
#endif
#include <PSHPACK1.H>
#define DIR_HOST_TO_DEVICE 0
#define DIR_DEVICE_TO_HOST 1
#define DEVICE_SPEED_UNKNOWN 0x00000000
#define DEVICE_SPEED_LOW_FULL 0x00000001
#define DEVICE_SPEED_HIGH 0x00000002
#define DEVICE_SPEED_SUPER 0x00000004
typedef struct _WORD_SPLIT {
UCHAR lowByte;
UCHAR hiByte;
} WORD_SPLIT, *PWORD_SPLIT;
typedef struct _BM_REQ_TYPE {
UCHAR Recipient:2;
UCHAR Reserved:3;
UCHAR Type:2;
UCHAR Direction:1;
} BM_REQ_TYPE, *PBM_REQ_TYPE;
typedef struct _SETUP_PACKET {
union {
BM_REQ_TYPE bmReqType;
UCHAR bmRequest;
};
UCHAR bRequest;
union {
WORD_SPLIT wVal;
USHORT wValue;
};
union {
WORD_SPLIT wIndx;
USHORT wIndex;
};
union {
WORD_SPLIT wLen;
USHORT wLength;
};
ULONG ulTimeOut;
} SETUP_PACKET, *PSETUP_PACKET;
#define USB_ISO_ID 0x4945
#define USB_ISO_CMD_ASAP 0x8000
#define USB_ISO_CMD_CURRENT_FRAME 0x8001
#define USB_ISO_CMD_SET_FRAME 0x8002
typedef struct _ISO_ADV_PARAMS {
USHORT isoId;
USHORT isoCmd;
ULONG ulParam1;
ULONG ulParam2;
} ISO_ADV_PARAMS, *PISO_ADV_PARAMS;
typedef struct _ISO_PACKET_INFO {
ULONG Status;
ULONG Length;
} ISO_PACKET_INFO, *PISO_PACKET_INFO;
typedef struct _SINGLE_TRANSFER {
union {
SETUP_PACKET SetupPacket;
ISO_ADV_PARAMS IsoParams;
};
UCHAR reserved;
UCHAR ucEndpointAddress;
ULONG NtStatus;
ULONG UsbdStatus;
ULONG IsoPacketOffset;
ULONG IsoPacketLength;
ULONG BufferOffset;
ULONG BufferLength;
} SINGLE_TRANSFER, *PSINGLE_TRANSFER;
#endif // #ifndef DRIVER
typedef struct _SET_TRANSFER_SIZE_INFO {
UCHAR EndpointAddress;
ULONG TransferSize;
} SET_TRANSFER_SIZE_INFO, *PSET_TRANSFER_SIZE_INFO;
//
// Macro to extract function out of the device io control code
//
#ifdef WIN_98_DDK
#define DEVICE_TYPE_FROM_CTL_CODE(ctrlCode) (((ULONG)(ctrlCode & 0xffff0000)) >> 16)
#endif
#define FUNCTION_FROM_CTL_CODE(ctrlCode) (((ULONG)(ctrlCode & 0x00003FFC)) >> 2)
#define ACCESS_FROM_CTL_CODE(ctrlCode) (((ULONG)(ctrlCode & 0x000C0000)) >> 14)
//#define METHOD_FROM_CTL_CODE(ctrlCode) (((ULONG)(ctrlCode & 0x00000003)))
#define IOCTL_ADAPT_INDEX 0x0000
// Get the driver version
#define IOCTL_ADAPT_GET_DRIVER_VERSION CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get the current USBDI version
#define IOCTL_ADAPT_GET_USBDI_VERSION CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+1, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get the current device alt interface settings from driver
#define IOCTL_ADAPT_GET_ALT_INTERFACE_SETTING CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+2, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Set the device interface and alt interface setting
#define IOCTL_ADAPT_SELECT_INTERFACE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+3, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get device address from driver
#define IOCTL_ADAPT_GET_ADDRESS CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+4, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get number of endpoints for current interface and alt interface setting from driver
#define IOCTL_ADAPT_GET_NUMBER_ENDPOINTS CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+5, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get the current device power state
#define IOCTL_ADAPT_GET_DEVICE_POWER_STATE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+6, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Set the device power state
#define IOCTL_ADAPT_SET_DEVICE_POWER_STATE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+7, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Send a raw packet to endpoint 0
#define IOCTL_ADAPT_SEND_EP0_CONTROL_TRANSFER CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+8, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Send/receive data to/from nonep0
#define IOCTL_ADAPT_SEND_NON_EP0_TRANSFER CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+9, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Simulate a disconnect/reconnect
#define IOCTL_ADAPT_CYCLE_PORT CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+10, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Reset the pipe
#define IOCTL_ADAPT_RESET_PIPE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+11, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Reset the device
#define IOCTL_ADAPT_RESET_PARENT_PORT CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+12, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get the current transfer size of an endpoint (in number of bytes)
#define IOCTL_ADAPT_GET_TRANSFER_SIZE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+13, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Set the transfer size of an endpoint (in number of bytes)
#define IOCTL_ADAPT_SET_TRANSFER_SIZE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+14, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Return the name of the device
#define IOCTL_ADAPT_GET_DEVICE_NAME CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+15, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Return the "Friendly Name" of the device
#define IOCTL_ADAPT_GET_FRIENDLY_NAME CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+16, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Abort all outstanding transfers on the pipe
#define IOCTL_ADAPT_ABORT_PIPE CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+17, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Send/receive data to/from nonep0 w/ direct buffer acccess (no buffering)
#define IOCTL_ADAPT_SEND_NON_EP0_DIRECT CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+18, METHOD_NEITHER, FILE_ANY_ACCESS)
// Return device speed
#define IOCTL_ADAPT_GET_DEVICE_SPEED CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+19, METHOD_BUFFERED, FILE_ANY_ACCESS)
// Get the current USB frame number
#define IOCTL_ADAPT_GET_CURRENT_FRAME CTL_CODE(FILE_DEVICE_UNKNOWN, IOCTL_ADAPT_INDEX+20, METHOD_BUFFERED, FILE_ANY_ACCESS)
#define NUMBER_OF_ADAPT_IOCTLS 21 // Last IOCTL_ADAPT_INDEX + 1
#include <POPPACK.H>
#endif // __IOCTL_H__

View File

@ -0,0 +1,184 @@
/*****************************************************************************
* *
* OpenNI 1.x Alpha *
* Copyright (C) 2012 PrimeSense Ltd. *
* *
* This file is part of OpenNI. *
* *
* Licensed under the Apache License, Version 2.0 (the "License"); *
* you may not use this file except in compliance with the License. *
* You may obtain a copy of the License at *
* *
* http://www.apache.org/licenses/LICENSE-2.0 *
* *
* Unless required by applicable law or agreed to in writing, software *
* distributed under the License is distributed on an "AS IS" BASIS, *
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. *
* See the License for the specific language governing permissions and *
* limitations under the License. *
* *
*****************************************************************************/
/*++ BUILD Version: 0004 // Increment this if a change has global effects
Copyright (c) 1992-1999 Microsoft Corporation
Module Name:
devioctl.h
Abstract:
This module contains
Revision History:
--*/
// begin_winioctl
#ifndef _DEVIOCTL_
#define _DEVIOCTL_
// begin_ntddk begin_wdm begin_nthal begin_ntifs
//
// Define the various device type values. Note that values used by Microsoft
// Corporation are in the range 0-32767, and 32768-65535 are reserved for use
// by customers.
//
#define DEVICE_TYPE ULONG
#define FILE_DEVICE_BEEP 0x00000001
#define FILE_DEVICE_CD_ROM 0x00000002
#define FILE_DEVICE_CD_ROM_FILE_SYSTEM 0x00000003
#define FILE_DEVICE_CONTROLLER 0x00000004
#define FILE_DEVICE_DATALINK 0x00000005
#define FILE_DEVICE_DFS 0x00000006
#define FILE_DEVICE_DISK 0x00000007
#define FILE_DEVICE_DISK_FILE_SYSTEM 0x00000008
#define FILE_DEVICE_FILE_SYSTEM 0x00000009
#define FILE_DEVICE_INPORT_PORT 0x0000000a
#define FILE_DEVICE_KEYBOARD 0x0000000b
#define FILE_DEVICE_MAILSLOT 0x0000000c
#define FILE_DEVICE_MIDI_IN 0x0000000d
#define FILE_DEVICE_MIDI_OUT 0x0000000e
#define FILE_DEVICE_MOUSE 0x0000000f
#define FILE_DEVICE_MULTI_UNC_PROVIDER 0x00000010
#define FILE_DEVICE_NAMED_PIPE 0x00000011
#define FILE_DEVICE_NETWORK 0x00000012
#define FILE_DEVICE_NETWORK_BROWSER 0x00000013
#define FILE_DEVICE_NETWORK_FILE_SYSTEM 0x00000014
#define FILE_DEVICE_NULL 0x00000015
#define FILE_DEVICE_PARALLEL_PORT 0x00000016
#define FILE_DEVICE_PHYSICAL_NETCARD 0x00000017
#define FILE_DEVICE_PRINTER 0x00000018
#define FILE_DEVICE_SCANNER 0x00000019
#define FILE_DEVICE_SERIAL_MOUSE_PORT 0x0000001a
#define FILE_DEVICE_SERIAL_PORT 0x0000001b
#define FILE_DEVICE_SCREEN 0x0000001c
#define FILE_DEVICE_SOUND 0x0000001d
#define FILE_DEVICE_STREAMS 0x0000001e
#define FILE_DEVICE_TAPE 0x0000001f
#define FILE_DEVICE_TAPE_FILE_SYSTEM 0x00000020
#define FILE_DEVICE_TRANSPORT 0x00000021
#define FILE_DEVICE_UNKNOWN 0x00000022
#define FILE_DEVICE_VIDEO 0x00000023
#define FILE_DEVICE_VIRTUAL_DISK 0x00000024
#define FILE_DEVICE_WAVE_IN 0x00000025
#define FILE_DEVICE_WAVE_OUT 0x00000026
#define FILE_DEVICE_8042_PORT 0x00000027
#define FILE_DEVICE_NETWORK_REDIRECTOR 0x00000028
#define FILE_DEVICE_BATTERY 0x00000029
#define FILE_DEVICE_BUS_EXTENDER 0x0000002a
#define FILE_DEVICE_MODEM 0x0000002b
#define FILE_DEVICE_VDM 0x0000002c
#define FILE_DEVICE_MASS_STORAGE 0x0000002d
#define FILE_DEVICE_SMB 0x0000002e
#define FILE_DEVICE_KS 0x0000002f
#define FILE_DEVICE_CHANGER 0x00000030
#define FILE_DEVICE_SMARTCARD 0x00000031
#define FILE_DEVICE_ACPI 0x00000032
#define FILE_DEVICE_DVD 0x00000033
#define FILE_DEVICE_FULLSCREEN_VIDEO 0x00000034
#define FILE_DEVICE_DFS_FILE_SYSTEM 0x00000035
#define FILE_DEVICE_DFS_VOLUME 0x00000036
#define FILE_DEVICE_SERENUM 0x00000037
#define FILE_DEVICE_TERMSRV 0x00000038
#define FILE_DEVICE_KSEC 0x00000039
#define FILE_DEVICE_FIPS 0x0000003A
#define FILE_DEVICE_INFINIBAND 0x0000003B
#define FILE_DEVICE_VMBUS 0x0000003E
#define FILE_DEVICE_CRYPT_PROVIDER 0x0000003F
#define FILE_DEVICE_WPD 0x00000040
#define FILE_DEVICE_BLUETOOTH 0x00000041
#define FILE_DEVICE_MT_COMPOSITE 0x00000042
#define FILE_DEVICE_MT_TRANSPORT 0x00000043
#define FILE_DEVICE_BIOMETRIC 0x00000044
#define FILE_DEVICE_PMI 0x00000045
//
// Macro definition for defining IOCTL and FSCTL function control codes. Note
// that function codes 0-2047 are reserved for Microsoft Corporation, and
// 2048-4095 are reserved for customers.
//
#define CTL_CODE( DeviceType, Function, Method, Access ) ( \
((DeviceType) << 16) | ((Access) << 14) | ((Function) << 2) | (Method) \
)
//
// Macro to extract device type out of the device io control code
//
#define DEVICE_TYPE_FROM_CTL_CODE(ctrlCode) (((ULONG)(ctrlCode & 0xffff0000)) >> 16)
//
// Macro to extract buffering method out of the device io control code
//
#define METHOD_FROM_CTL_CODE(ctrlCode) ((ULONG)(ctrlCode & 3))
//
// Define the method codes for how buffers are passed for I/O and FS controls
//
#define METHOD_BUFFERED 0
#define METHOD_IN_DIRECT 1
#define METHOD_OUT_DIRECT 2
#define METHOD_NEITHER 3
//
// Define some easier to comprehend aliases:
// METHOD_DIRECT_TO_HARDWARE (writes, aka METHOD_IN_DIRECT)
// METHOD_DIRECT_FROM_HARDWARE (reads, aka METHOD_OUT_DIRECT)
//
#define METHOD_DIRECT_TO_HARDWARE METHOD_IN_DIRECT
#define METHOD_DIRECT_FROM_HARDWARE METHOD_OUT_DIRECT
//
// Define the access check value for any access
//
//
// The FILE_READ_ACCESS and FILE_WRITE_ACCESS constants are also defined in
// ntioapi.h as FILE_READ_DATA and FILE_WRITE_DATA. The values for these
// constants *MUST* always be in sync.
//
//
// FILE_SPECIAL_ACCESS is checked by the NT I/O system the same as FILE_ANY_ACCESS.
// The file systems, however, may add additional access checks for I/O and FS controls
// that use this value.
//
#define FILE_ANY_ACCESS 0
#define FILE_SPECIAL_ACCESS (FILE_ANY_ACCESS)
#define FILE_READ_ACCESS ( 0x0001 ) // file & pipe
#define FILE_WRITE_ACCESS ( 0x0002 ) // file & pipe
// end_ntddk end_wdm end_nthal end_ntifs
#endif // _DEVIOCTL_
// end_winioctl

View File

@ -0,0 +1,208 @@
// MIT License Copyright (c) 2016 Booya Corp.
// booyasdr@gmail.com, http://booyasdr.sf.net
// modified 2017 11 30 ik1xpv@gmail.com, http://www.steila.com/blog
#include <windows.h>
#include <sys/stat.h>
#include <iostream>
#include <stdio.h>
#include "openfx3.h"
#include <spdlog/spdlog.h>
#define DbgPrintf spdlog::info
using namespace std;
void fx3Control(FX3Command command) { // firmware control
long lgt = 1;
UINT8 z = 0; // dummy data = 0
fx3dev->ControlEndPt->ReqCode = command;
fx3dev->ControlEndPt->Write(&z, lgt);
}
bool fx3Control(FX3Command command, PUINT8 data) { // firmware control BBRF
long lgt = 1; // default
bool r = false;
switch (command)
{
case GPIOFX3:
fx3dev->ControlEndPt->ReqCode = command;
fx3dev->ControlEndPt->Value = (USHORT)0;
fx3dev->ControlEndPt->Index = (USHORT)0;
lgt = 2;
DbgPrintf("GPIO %x %x\n", data[0], data[1]);
r = fx3dev->ControlEndPt->Write(data, lgt);
break;
case TESTFX3:
fx3dev->ControlEndPt->ReqCode = command;
fx3dev->ControlEndPt->Value = (USHORT)0;
fx3dev->ControlEndPt->Index = (USHORT)0;
lgt = 4; // TESTFX3 len
r = fx3dev->ControlEndPt->Read(data, lgt);
break;
default:
break;
}
if (r == false)
{
DbgPrintf("WARNING FX3FWControl failed %x .%x %x\n", r, command, *data);
closeFX3();
}
return r;
}
bool fx3SendI2cbytes(UINT8 i2caddr, UINT8 regaddr, PUINT8 pdata, UINT8 len)
{
bool r = false;
LONG lgt = len;
fx3dev->ControlEndPt->ReqCode = I2CWFX3;
fx3dev->ControlEndPt->Value = (USHORT)i2caddr;
fx3dev->ControlEndPt->Index = (USHORT)regaddr;
Sleep(10);
r = fx3dev->ControlEndPt->Write(pdata, lgt);
if (r == false)
DbgPrintf("\nWARNING fx3FWSendI2cbytes i2caddr 0x%02x regaddr 0x%02x 1data 0x%02x len 0x%02x \n",
i2caddr, regaddr, *pdata, len);
return r;
}
bool fx3SendI2cbyte(UINT8 i2caddr, UINT8 regaddr, UINT8 data)
{
return fx3SendI2cbytes(i2caddr, regaddr, &data, 1);
}
bool fx3ReadI2cbytes(UINT8 i2caddr, UINT8 regaddr, PUINT8 pdata, UINT8 len)
{
bool r = false;
LONG lgt = len;
WORD saveValue, saveIndex;
saveValue = fx3dev->ControlEndPt->Value;
saveIndex = fx3dev->ControlEndPt->Index;
fx3dev->ControlEndPt->ReqCode = I2CRFX3;
fx3dev->ControlEndPt->Value = (USHORT)i2caddr;
fx3dev->ControlEndPt->Index = (USHORT)regaddr;
r = fx3dev->ControlEndPt->Read(pdata, lgt);
if (r == false)
printf("WARNING fx3FWReadI2cbytes failed %x : %02x %02x %02x %02x : %02x\n", r, I2CRFX3, i2caddr, regaddr, len, *pdata);
fx3dev->ControlEndPt->Value = saveValue;
fx3dev->ControlEndPt->Index = saveIndex;
return r;
}
bool fx3ReadI2cbyte(UINT8 i2caddr, UINT8 regaddr, UINT8 data)
{
return fx3ReadI2cbytes(i2caddr, regaddr, &data, 1);
}
bool GetFx3Device(void); // open the device, called in initFX3()
CCyFX3Device *fx3dev = NULL;
const int VENDOR_ID = 0x04B4;
const int STREAMER_ID = 0x00F1;
const int BOOTLOADER_ID = 0x00F3;
CCyUSBEndPoint *EndPt;
bool bHighSpeedDevice;
bool bSuperSpeedDevice;
bool openFX3() {
bool r = false;
fx3dev = new CCyFX3Device; // instantiate the device
if (fx3dev == NULL) return 0; // return if failed
int n = fx3dev->DeviceCount(); // return if no devices connected
if (n == 0) {
DbgPrintf("Device Count = 0, Exit\n");
return r;
}
if (!GetFx3Device()) { DbgPrintf("No streamer or boot device found, Exit\n"); return r; }
char fwname[] = "rx888.img"; // firmware file
if (!fx3dev->IsBootLoaderRunning()) { // if not bootloader device
fx3Control(RESETFX3); // reset the fx3 firmware via CyU3PDeviceReset(false)
DbgPrintf("Reset Device\n");
Sleep(300);
fx3dev->Close(); // close class
delete fx3dev; // destroy class
Sleep(300);
fx3dev = new CCyFX3Device; // create class
GetFx3Device(); // open class
}
FX3_FWDWNLOAD_ERROR_CODE dlf = FAILED;
if (fx3dev->IsBootLoaderRunning()) {
dlf = fx3dev->DownloadFw(fwname, RAM);
Sleep(500); // wait for download to finish
}
if (dlf == 0) {
struct stat stbuf;
stat(fwname, &stbuf);
char *timestr;
timestr = ctime(&stbuf.st_mtime);
DbgPrintf("Loaded NEW FIRMWARE {0} {1}", fwname, timestr);
}
else if (dlf != 0)
{
DbgPrintf("OLD FIRMWARE\n");
}
GetFx3Device(); // open class with new firmware
if (!fx3dev->IsOpen()) {
DbgPrintf("Failed to open device\n");
return r;
}
EndPt = fx3dev->BulkInEndPt;
if (!EndPt) {
DbgPrintf("No Bulk In end point\n");
return r; // init failed
}
r = true;
return r; // init success
}
bool closeFX3() {
bool r = false;
fx3dev->Close(); // close class
delete fx3dev; // destroy class
Sleep(300);
return r;
}
bool GetFx3Device() { // open class
bool r = false;
if (fx3dev == NULL) return r;
int n = fx3dev->DeviceCount();
// Walk through all devices looking for VENDOR_ID/STREAMER_ID
if (n == 0) { DbgPrintf("Device Count = 0, Exit\n"); return r; }
fx3dev->Open(0);
// go down the list of devices to find our device
for (int i = 1; i <= n; i++) {
cout << hex << fx3dev->VendorID << " "
<< hex << fx3dev->ProductID << " " << fx3dev->FriendlyName << '\n';
if ((fx3dev->VendorID == VENDOR_ID) && (fx3dev->ProductID == STREAMER_ID))
{
r = true;
break;
}
if ((fx3dev->VendorID == VENDOR_ID) && (fx3dev->ProductID == BOOTLOADER_ID))
{
r = true;
break;
}
fx3dev->Open(i);
}
if (r == false)
fx3dev->Close();
return r;
}
bool fx3Check()
{
return (fx3dev != NULL);
}

View File

@ -0,0 +1,36 @@
// MIT License Copyright (c) 2016 Booya Corp.
// booyasdr@gmail.com, http://booyasdr.sf.net
// modified 2017 11 30 ik1xpv@gmail.com, http://www.steila.com/blog
#ifndef FX3DEV_H
#define FX3DEV_H
#include <windows.h>
#include "CyAPI.h"
#define PUINT8 UINT8*
bool openFX3(void);
extern CCyFX3Device *fx3dev;
extern CCyUSBEndPoint *EndPt;
bool closeFX3(void);
enum FX3Command {
STARTFX3 = 0xaa,
STOPFX3 = 0xab,
TESTFX3 = 0xac,
RESETFX3 = 0xcc,
PAUSEFX3 = 0xdd,
GPIOFX3 = 0xbc,
I2CWFX3 = 0xba,
I2CRFX3 = 0xbe
};
void fx3Control(FX3Command command);
bool fx3Control(FX3Command command, PUINT8 data);
bool fx3SendI2cbytes(UINT8 i2caddr, UINT8 regaddr, PUINT8 pdata, UINT8 len);
bool fx3SendI2cbyte(UINT8 i2caddr, UINT8 regaddr, UINT8 pdata);
bool fx3ReadI2cbytes(UINT8 i2caddr, UINT8 regaddr, PUINT8 pdata, UINT8 len);
bool fx3ReadI2cbyte(UINT8 i2caddr, UINT8 regaddr, UINT8 pdata);
bool fx3Check();
#endif

View File

@ -0,0 +1,270 @@
#ifndef __USB100_H__
#define __USB100_H__
#include <PSHPACK1.H>
//bmRequest.Dir
#define BMREQUEST_HOST_TO_DEVICE 0
#define BMREQUEST_DEVICE_TO_HOST 1
//bmRequest.Type
#define BMREQUEST_STANDARD 0
#define BMREQUEST_CLASS 1
#define BMREQUEST_VENDOR 2
//bmRequest.Recipient
#define BMREQUEST_TO_DEVICE 0
#define BMREQUEST_TO_INTERFACE 1
#define BMREQUEST_TO_ENDPOINT 2
#define BMREQUEST_TO_OTHER 3
#define MAXIMUM_USB_STRING_LENGTH 255
// values for the bits returned by the USB GET_STATUS command
#define USB_GETSTATUS_SELF_POWERED 0x01
#define USB_GETSTATUS_REMOTE_WAKEUP_ENABLED 0x02
#define USB_DEVICE_DESCRIPTOR_TYPE 0x01
#define USB_CONFIGURATION_DESCRIPTOR_TYPE 0x02
#define USB_STRING_DESCRIPTOR_TYPE 0x03
#define USB_INTERFACE_DESCRIPTOR_TYPE 0x04
#define USB_ENDPOINT_DESCRIPTOR_TYPE 0x05
// descriptor types defined by DWG documents
#define USB_RESERVED_DESCRIPTOR_TYPE 0x06
#define USB_CONFIG_POWER_DESCRIPTOR_TYPE 0x07
#define USB_INTERFACE_POWER_DESCRIPTOR_TYPE 0x08
#define USB_DESCRIPTOR_MAKE_TYPE_AND_INDEX(d, i) ((USHORT)((USHORT)d<<8 | i))
//
// Values for bmAttributes field of an
// endpoint descriptor
//
#define USB_ENDPOINT_TYPE_MASK 0x03
#define USB_ENDPOINT_TYPE_CONTROL 0x00
#define USB_ENDPOINT_TYPE_ISOCHRONOUS 0x01
#define USB_ENDPOINT_TYPE_BULK 0x02
#define USB_ENDPOINT_TYPE_INTERRUPT 0x03
//
// definitions for bits in the bmAttributes field of a
// configuration descriptor.
//
#define USB_CONFIG_POWERED_MASK 0xc0
#define USB_CONFIG_BUS_POWERED 0x80
#define USB_CONFIG_SELF_POWERED 0x40
#define USB_CONFIG_REMOTE_WAKEUP 0x20
//
// Endpoint direction bit, stored in address
//
#define USB_ENDPOINT_DIRECTION_MASK 0x80
// test direction bit in the bEndpointAddress field of
// an endpoint descriptor.
#define USB_ENDPOINT_DIRECTION_OUT(addr) (!((addr) & USB_ENDPOINT_DIRECTION_MASK))
#define USB_ENDPOINT_DIRECTION_IN(addr) ((addr) & USB_ENDPOINT_DIRECTION_MASK)
//
// USB defined request codes
// see chapter 9 of the USB 1.0 specifcation for
// more information.
//
// These are the correct values based on the USB 1.0
// specification
#define USB_REQUEST_GET_STATUS 0x00
#define USB_REQUEST_CLEAR_FEATURE 0x01
#define USB_REQUEST_SET_FEATURE 0x03
#define USB_REQUEST_SET_ADDRESS 0x05
#define USB_REQUEST_GET_DESCRIPTOR 0x06
#define USB_REQUEST_SET_DESCRIPTOR 0x07
#define USB_REQUEST_GET_CONFIGURATION 0x08
#define USB_REQUEST_SET_CONFIGURATION 0x09
#define USB_REQUEST_GET_INTERFACE 0x0A
#define USB_REQUEST_SET_INTERFACE 0x0B
#define USB_REQUEST_SYNC_FRAME 0x0C
//
// defined USB device classes
//
#define USB_DEVICE_CLASS_RESERVED 0x00
#define USB_DEVICE_CLASS_AUDIO 0x01
#define USB_DEVICE_CLASS_COMMUNICATIONS 0x02
#define USB_DEVICE_CLASS_HUMAN_INTERFACE 0x03
#define USB_DEVICE_CLASS_MONITOR 0x04
#define USB_DEVICE_CLASS_PHYSICAL_INTERFACE 0x05
#define USB_DEVICE_CLASS_POWER 0x06
#define USB_DEVICE_CLASS_PRINTER 0x07
#define USB_DEVICE_CLASS_STORAGE 0x08
#define USB_DEVICE_CLASS_HUB 0x09
#define USB_DEVICE_CLASS_VENDOR_SPECIFIC 0xFF
//
// USB Core defined Feature selectors
//
#define USB_FEATURE_ENDPOINT_STALL 0x0000
#define USB_FEATURE_REMOTE_WAKEUP 0x0001
//
// USB DWG defined Feature selectors
//
#define USB_FEATURE_INTERFACE_POWER_D0 0x0002
#define USB_FEATURE_INTERFACE_POWER_D1 0x0003
#define USB_FEATURE_INTERFACE_POWER_D2 0x0004
#define USB_FEATURE_INTERFACE_POWER_D3 0x0005
typedef struct _USB_DEVICE_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
USHORT bcdUSB;
UCHAR bDeviceClass;
UCHAR bDeviceSubClass;
UCHAR bDeviceProtocol;
UCHAR bMaxPacketSize0;
USHORT idVendor;
USHORT idProduct;
USHORT bcdDevice;
UCHAR iManufacturer;
UCHAR iProduct;
UCHAR iSerialNumber;
UCHAR bNumConfigurations;
} USB_DEVICE_DESCRIPTOR, *PUSB_DEVICE_DESCRIPTOR;
typedef struct _USB_ENDPOINT_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bEndpointAddress;
UCHAR bmAttributes;
USHORT wMaxPacketSize;
UCHAR bInterval;
} USB_ENDPOINT_DESCRIPTOR, *PUSB_ENDPOINT_DESCRIPTOR;
typedef struct _USB_CONFIGURATION_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
USHORT wTotalLength;
UCHAR bNumInterfaces;
UCHAR bConfigurationValue;
UCHAR iConfiguration;
UCHAR bmAttributes;
UCHAR MaxPower;
} USB_CONFIGURATION_DESCRIPTOR, *PUSB_CONFIGURATION_DESCRIPTOR;
typedef struct _USB_INTERFACE_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bInterfaceNumber;
UCHAR bAlternateSetting;
UCHAR bNumEndpoints;
UCHAR bInterfaceClass;
UCHAR bInterfaceSubClass;
UCHAR bInterfaceProtocol;
UCHAR iInterface;
} USB_INTERFACE_DESCRIPTOR, *PUSB_INTERFACE_DESCRIPTOR;
typedef struct _USB_STRING_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
WCHAR bString[1];
} USB_STRING_DESCRIPTOR, *PUSB_STRING_DESCRIPTOR;
typedef struct _USB_COMMON_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
} USB_COMMON_DESCRIPTOR, *PUSB_COMMON_DESCRIPTOR;
//
// Standard USB HUB definitions
//
// See Chapter 11 USB core specification
//
typedef struct _USB_HUB_DESCRIPTOR {
UCHAR bDescriptorLength; // Length of this descriptor
UCHAR bDescriptorType; // Hub configuration type
UCHAR bNumberOfPorts; // number of ports on this hub
USHORT wHubCharacteristics; // Hub Charateristics
UCHAR bPowerOnToPowerGood; // port power on till power good in 2ms
UCHAR bHubControlCurrent; // max current in mA
//
// room for 255 ports power control and removable bitmask
UCHAR bRemoveAndPowerMask[64];
} USB_HUB_DESCRIPTOR, *PUSB_HUB_DESCRIPTOR;
//
// Structures defined by various DWG feature documents
//
//
// See DWG USB Feature Specification: Interface Power Management
//
#define USB_SUPPORT_D0_COMMAND 0x01
#define USB_SUPPORT_D1_COMMAND 0x02
#define USB_SUPPORT_D2_COMMAND 0x04
#define USB_SUPPORT_D3_COMMAND 0x08
#define USB_SUPPORT_D1_WAKEUP 0x10
#define USB_SUPPORT_D2_WAKEUP 0x20
typedef struct _USB_CONFIGURATION_POWER_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR SelfPowerConsumedD0[3];
UCHAR bPowerSummaryId;
UCHAR bBusPowerSavingD1;
UCHAR bSelfPowerSavingD1;
UCHAR bBusPowerSavingD2;
UCHAR bSelfPowerSavingD2;
UCHAR bBusPowerSavingD3;
UCHAR bSelfPowerSavingD3;
USHORT TransitionTimeFromD1;
USHORT TransitionTimeFromD2;
USHORT TransitionTimeFromD3;
} USB_CONFIGURATION_POWER_DESCRIPTOR, *PUSB_CONFIGURATION_POWER_DESCRIPTOR;
typedef struct _USB_INTERFACE_POWER_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bmCapabilitiesFlags;
UCHAR bBusPowerSavingD1;
UCHAR bSelfPowerSavingD1;
UCHAR bBusPowerSavingD2;
UCHAR bSelfPowerSavingD2;
UCHAR bBusPowerSavingD3;
UCHAR bSelfPowerSavingD3;
USHORT TransitionTimeFromD1;
USHORT TransitionTimeFromD2;
USHORT TransitionTimeFromD3;
} USB_INTERFACE_POWER_DESCRIPTOR, *PUSB_INTERFACE_POWER_DESCRIPTOR;
#include <POPPACK.H>
#endif /* __USB100_H__ */

View File

@ -0,0 +1,111 @@
#ifndef __USB200_H__
#define __USB200_H__
#include "usb100.h"
#include <PSHPACK1.H>
typedef enum _USB_DEVICE_SPEED {
UsbLowSpeed = 0,
UsbFullSpeed,
UsbHighSpeed
} USB_DEVICE_SPEED;
typedef enum _USB_DEVICE_TYPE {
Usb11Device = 0,
Usb20Device
} USB_DEVICE_TYPE;
// standard definiions for the port status
// word of the HUB port register
#define USB_PORT_STATUS_CONNECT 0x0001
#define USB_PORT_STATUS_ENABLE 0x0002
#define USB_PORT_STATUS_SUSPEND 0x0004
#define USB_PORT_STATUS_OVER_CURRENT 0x0008
#define USB_PORT_STATUS_RESET 0x0010
#define USB_PORT_STATUS_POWER 0x0100
#define USB_PORT_STATUS_LOW_SPEED 0x0200
#define USB_PORT_STATUS_HIGH_SPEED 0x0400
typedef union _BM_REQUEST_TYPE {
struct _BM {
UCHAR Recipient:2;
UCHAR Reserved:3;
UCHAR Type:2;
UCHAR Dir:1;
};
UCHAR B;
} BM_REQUEST_TYPE, *PBM_REQUEST_TYPE;
typedef struct _USB_DEFAULT_PIPE_SETUP_PACKET {
BM_REQUEST_TYPE bmRequestType;
UCHAR bRequest;
union _wValue {
struct {
UCHAR LowByte;
UCHAR HiByte;
};
USHORT W;
} wValue;
union _wIndex {
struct {
UCHAR LowByte;
UCHAR HiByte;
};
USHORT W;
} wIndex;
USHORT wLength;
} USB_DEFAULT_PIPE_SETUP_PACKET, *PUSB_DEFAULT_PIPE_SETUP_PACKET;
// setup packet is eight bytes -- defined by spec
C_ASSERT(sizeof(USB_DEFAULT_PIPE_SETUP_PACKET) == 8);
#define USB_DEVICE_QUALIFIER_DESCRIPTOR_TYPE 0x06
typedef struct _USB_DEVICE_QUALIFIER_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
USHORT bcdUSB;
UCHAR bDeviceClass;
UCHAR bDeviceSubClass;
UCHAR bDeviceProtocol;
UCHAR bMaxPacketSize0;
UCHAR bNumConfigurations;
UCHAR bReserved;
} USB_DEVICE_QUALIFIER_DESCRIPTOR, *PUSB_DEVICE_QUALIFIER_DESCRIPTOR;
typedef union _USB_HIGH_SPEED_MAXPACKET {
struct _MP {
USHORT MaxPacket:11; /* 0..10 */
USHORT HSmux:2; /* 11..12 */
USHORT Reserved:3; /* 13..15 */
};
USHORT us;
} USB_HIGH_SPEED_MAXPACKET, *PUSB_HIGH_SPEED_MAXPACKET;
#define USB_INTERFACE_ASSOCIATION_DESCRIPTOR_TYPE 0x0B
typedef struct _USB_INTERFACE_ASSOCIATION_DESCRIPTOR {
UCHAR bLength;
UCHAR bDescriptorType;
UCHAR bFirstInterface;
UCHAR bInterfaceCount;
UCHAR bFunctionClass;
UCHAR bFunctionSubClass;
UCHAR bFunctionProtocol;
UCHAR iFunction;
} USB_INTERFACE_ASSOCIATION_DESCRIPTOR, *PUSB_INTERFACE_ASSOCIATION_DESCRIPTOR;
#include <POPPACK.H>
#endif // __USB200_H__

177
rx888_source/src/main.cpp Normal file
View File

@ -0,0 +1,177 @@
#include <imgui.h>
#include <spdlog/spdlog.h>
#include <module.h>
#include <gui/gui.h>
#include <signal_path/signal_path.h>
#include <core.h>
#include <gui/style.h>
#include <openFX3.h>
#include <Si5351.h>
#define CONCAT(a, b) ((std::string(a) + b).c_str())
#define SEL0 (8) // SEL0 GPIO26
#define SEL1 (16) // SEL1 GPIO27
MOD_INFO {
/* Name: */ "rx888_source",
/* Description: */ "RX888 input module for SDR++",
/* Author: */ "Ryzerth",
/* Version: */ "0.1.0"
};
class RX888SourceModule {
public:
RX888SourceModule(std::string name) {
this->name = name;
if (!openFX3()) {
spdlog::error("No RX888 found!");
return;
}
Si5351init();
sampleRate = 8000000;
handler.ctx = this;
handler.selectHandler = menuSelected;
handler.deselectHandler = menuDeselected;
handler.menuHandler = menuHandler;
handler.startHandler = start;
handler.stopHandler = stop;
handler.tuneHandler = tune;
handler.stream = &stream;
sigpath::sourceManager.registerSource("RX888", &handler);
spdlog::info("RX888SourceModule '{0}': Instance created!", name);
}
~RX888SourceModule() {
spdlog::info("RX888SourceModule '{0}': Instance deleted!", name);
}
private:
static void menuSelected(void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
spdlog::info("RX888SourceModule '{0}': Menu Select!", _this->name);
core::setInputSampleRate(_this->sampleRate);
}
static void menuDeselected(void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
spdlog::info("RX888SourceModule '{0}': Menu Deselect!", _this->name);
}
static void start(void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
_this->doStart();
spdlog::info("RX888SourceModule '{0}': Start!", _this->name);
}
void doStart() {
uint8_t Bgpio[2];
Bgpio[0] = 0x17 | SEL0 & (~SEL1);
Bgpio[1] = 0x00;
si5351aSetFrequency(sampleRate * 2, 0);
fx3Control(GPIOFX3, Bgpio);
running = true;
workerThread = std::thread(_worker, this);
}
static void stop(void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
_this->running = false;
_this->workerThread.join();
spdlog::info("RX888SourceModule '{0}': Stop!", _this->name);
}
static void tune(double freq, void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
_this->freq = freq;
spdlog::info("RX888SourceModule '{0}': Tune: {1}!", _this->name, freq);
}
static void menuHandler(void* ctx) {
RX888SourceModule* _this = (RX888SourceModule*)ctx;
ImGui::Text("RX888 source");
}
static void _worker(RX888SourceModule* _this) {
int blockSize = _this->sampleRate / 200.0f;
if ((blockSize % 2) != 0) { blockSize++; }
int flags = 0;
long long timeMs = 0;
int16_t* buffer = new int16_t[blockSize * 2];
long pktSize = EndPt->MaxPktSize;
EndPt->SetXferSize(blockSize * 2);
long ppx = blockSize * 2 / pktSize;
OVERLAPPED inOvLap;
inOvLap.hEvent = CreateEvent(NULL, false, false, NULL);
auto context = EndPt->BeginDataXfer((PUCHAR)buffer, blockSize, &inOvLap);
fx3Control(STARTFX3);
while (_this->running) {
//if (_this->stream.aquire() < 0) { break; }
LONG rLen = blockSize * 2;
if (!EndPt->WaitForXfer(&inOvLap, 5000)) {
spdlog::error("Transfer aborted");
EndPt->Abort();
if (EndPt->LastError == ERROR_IO_PENDING) {
WaitForSingleObject(inOvLap.hEvent, 5000);
}
break;
}
if (EndPt->Attributes == 2) {
if (EndPt->FinishDataXfer((PUCHAR)buffer, rLen, &inOvLap, context)) {
spdlog::warn("{0}", rLen);
}
}
context = EndPt->BeginDataXfer((PUCHAR)buffer, blockSize, &inOvLap);
}
delete[] buffer;
}
std::string name;
dsp::stream<dsp::complex_t> stream;
SourceManager::SourceHandler handler;
std::thread workerThread;
double freq;
double sampleRate;
bool running = false;
};
MOD_EXPORT void _INIT_() {
}
MOD_EXPORT void* _CREATE_INSTANCE_(std::string name) {
return new RX888SourceModule(name);
}
MOD_EXPORT void _DELETE_INSTANCE_(void* instance) {
delete (RX888SourceModule*)instance;
}
MOD_EXPORT void _STOP_() {
}