Senin, 20 April 2015

MENGONTROL RELAY VIA USB MENGGUNAKAN BASIC Dan USB 2-RELAY

Mengontrol Relay Via USB Menggunakan USB-2REL


DESKRIPSI:
USB-2REL adalah modul USB Relay yang memiliki 2 buah relay sebagai output. Dengan modul ini kita bisa mengendalikan kondisi 2 buah relay (on/off) melalui program komputer dengan antarmuka port USB.

Modul ini mengambil daya secara langsung dari port USB sehingga tidak membutuhkan catu daya eksternal. Oleh karenanya modul USB-2REL sangat mudah dan praktis digunakan.

Modul dilengkapi dengan kabel data USB dengan panjang 1,5m dan CD yang berisi driver dan contoh-contoh program aplikasi.
SPESIFIKASI:
Tegangan kerja                        : DC 5V (USB Powered - tidak perlu catudaya eksternal)
Jumlah Output                                    : 2 buah
Tipe Output                             : Relay (Kontak NO=10A, Kontak NC=6A @250VAC)
Konektor Relay                       : Terminal Screw
Mikrokontroler                        : AVR ATtiny2313
Kabel data                               : USB konektor tipe B - 1,5 meter
3 LED Indikator                     : Power ON, Relay-1 ON, Relay-2 ON
Watchdog Timer                     : 30ms
Sistem Operasi                        : Win98, Win2000, WinXP, Win7, WinVista, Linux, Raspian
Software Driver                      : LIBUSB
Command-Line Tools             : usb2rc.exe (Win), usb2rc (Linux), usb2rc (Raspi)
Dilengkapi contoh program    : C, Delphi, Lazarus, JustBASIC, PHP, Python, Raspberry Pi,
REBOL, VB, VB.NET
Contoh Program:
/****************************************************************************
 *                                                                                                                                                    *
 * File    : main.c                                                                                                                            *
 *                                                                                                                                                    *
 * Purpose : Generic dialog based Win32 application.                                                                  *
 *                                                                                                                                                    *
 * History : Date      Reason                                                                                                           *
 *           00/00/00  Created                                                                                                            *
 *                                                                                                                                                    *
 ****************************************************************************/
/*
 * Either define WIN32_LEAN_AND_MEAN, or one or more of NOCRYPT,
 * NOSERVICE, NOMCX and NOIME, to decrease compile time (if you
 * don't need these defines -- see windows.h).
 */
#define WIN32_LEAN_AND_MEAN
/* #define NOCRYPT */
/* #define NOSERVICE */
/* #define NOMCX */
/* #define NOIME */
#include <windows.h>
#include <windowsx.h>
#include <commctrl.h>
#include <commdlg.h>
#include <tchar.h>
#include "main.h"
#include <lusb0_usb.h>
#include <stdio.h>
#include <process.h>
#include <excpt.h>
#define NELEMS(a)  (sizeof(a) / sizeof((a)[0]))
#define USBDEV_SHARED_VENDOR    0x16C0  /* VOTI */
#define USBDEV_SHARED_PRODUCT   0x05DC  /* Obdev's free shared PID */
/* Perintah-perintah yang digunakan Host pada USB Crypto Dongle */
#define PSCMD_ASKID                  0
#define PSCMD_CONTROL            1
#define PSCMD_ALLON                 2
#define PSCMD_ALLOFF    3
/** Prototypes **************************************************************/
static INT_PTR CALLBACK MainDlgProc(HWND, UINT, WPARAM, LPARAM);
//static LRESULT CALLBACK MainDlgProc(HWND, UINT, WPARAM, LPARAM);
static int  usbGetStringAscii(usb_dev_handle *dev, int index, int langid, char *buf, int buflen);
static int usbOpenDevice(usb_dev_handle **device, int vendor, char *vendorName, int product, char *productName);
/** Global variables ********************************************************/
usb_dev_handle    *handle = NULL;
static HANDLE     ghInstance;
/****************************************************************************
 *                                                                                                                                                    *
 * Function: WinMain                                                                                                                   *
 *                                                                                                                                                   *
 * Purpose : Initialize the application.  Register a window class,                                                 *
 *           create and display the main window and enter the                                                         *
 *           message loop.                                                                                                                  *
 *                                                                                                                                                    *
 * History : Date      Reason                                                                                                          *
 *           00/00/00  Created                                                                                                           *
 *                                                                                                                                                   *
 ****************************************************************************/
int PASCAL WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdLine, int nCmdShow)
{
    INITCOMMONCONTROLSEX icc;
    WNDCLASSEX wcx;
    ghInstance = hInstance;
    /* Initialize common controls. Also needed for MANIFEST's */
    /*
     * TODO: set the ICC_???_CLASSES that you need.
     */
    icc.dwSize = sizeof(icc);
    icc.dwICC = ICC_WIN95_CLASSES /*|ICC_COOL_CLASSES|ICC_DATE_CLASSES|ICC_PAGESCROLLER_CLASS|ICC_USEREX_CLASSES|... */;
    InitCommonControlsEx(&icc);
    /* Load Rich Edit control support */
    /*
     * TODO: uncomment one of the lines below, if you are using a Rich Edit control.
     */
    // LoadLibrary(_T("riched32.dll"));  // Rich Edit v1.0
    // LoadLibrary(_T("riched20.dll"));  // Rich Edit v2.0, v3.0
    /*
     * TODO: uncomment line below, if you are using the Network Address control (Windows Vista+).
     */
    // InitNetworkAddressControl();
    /* Get system dialog information */
    wcx.cbSize = sizeof(wcx);
    if (!GetClassInfoEx(NULL, MAKEINTRESOURCE(32770), &wcx))
        return 0;
    /* Add our own stuff */
    wcx.hInstance = hInstance;
    wcx.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDR_ICO_MAIN));
    wcx.lpszClassName = _T("USB2RELClass");
    if (!RegisterClassEx(&wcx))
        return 0;
    /* The user interface is a modal dialog box */
    return DialogBox(hInstance, MAKEINTRESOURCE(DLG_MAIN), NULL, (DLGPROC)MainDlgProc);
}
/****************************************************************************
 *                                                                                                                                                    *
 * Function: MainDlgProc                                                                                                             *
 *                                                                                                                                                    *
 * Purpose : Process messages for the Main dialog.                                                                      *
 *                                                                                                                                                    *
 * History : Date      Reason                                                                                                          *
 *           00/00/00  Created                                                                                                            *
 *                                                                                                                                                    *
 ****************************************************************************/
static INT_PTR CALLBACK MainDlgProc(HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
            unsigned char nBytes, xx;
            char buffer[64];
    switch (uMsg)
    {
        case WM_INITDIALOG:
                                    //Inisialisasi port USB
                                    usb_init();
                                    //Buka komunikasi USB dengan USBCrypto Dongle
                        if(usbOpenDevice(&handle, USBDEV_SHARED_VENDOR, "Teknik Elektro Links", USBDEV_SHARED_PRODUCT, "TELINKS-USB2REL") != 0)
                        {
                        MessageBox(hwndDlg, "Modul TELINKS-USB2REL tidak ditemukan!", "Error!", MB_ICONERROR);
                        exit(1);
                        }
            return TRUE;
        case WM_SIZE:
            /*
             * TODO: Add code to process resizing, when needed.
             */
            return TRUE;
        case WM_COMMAND:
            switch (GET_WM_COMMAND_ID(wParam, lParam))
            {
                                                case ID_ASK_ID:
                                                            nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_ASKID, 0, 0, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                                            else
                                                                        SetDlgItemText(hwndDlg, ID_EDIT1, (char*)buffer);
                                   
                                                            return TRUE;
                case ID_RL1_ON:
                                    nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_CONTROL, 1, 1, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                                            else
                                                                        SetDlgItemText(hwndDlg, ID_EDIT1, (char*)buffer);
                                    return TRUE;
                        case ID_RL1_OFF:
                                    nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_CONTROL, 0, 1, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                    return TRUE;
                        case ID_RL2_ON:
                                                            nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                                            PSCMD_CONTROL, 1, 2, (char *)buffer, sizeof(buffer), 5000);
                                                if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                                           
                    return TRUE;
                        case ID_RL2_OFF:
                                    nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_CONTROL, 0, 2, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                    return TRUE;
                                                case ID_ALL_ON:
                                                            nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_ALLON, 0, 0, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                    return TRUE;
                                                case ID_ALL_OFF:
                                                            nBytes = usb_control_msg(handle, USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_ENDPOINT_IN,
                                    PSCMD_ALLOFF, 0, 0, (char *)buffer, sizeof(buffer), 5000);
                                    if (nBytes<0)
                                                MessageBox(hwndDlg, usb_strerror(), "Error!", MB_ICONINFORMATION);
                                    return TRUE;
       
                case IDOK:
                    EndDialog(hwndDlg, TRUE);
                    return TRUE;
            }
            break;
        case WM_CLOSE:
                                    usb_close(handle);
            EndDialog(hwndDlg, 0);
            return TRUE;
        /*
         * TODO: Add more messages, when needed.
         */
    }
    return FALSE;
}
/*
  Fungsi-fungsi komunikasi data USB
*/
static int  usbGetStringAscii(usb_dev_handle *dev, int index, int langid, char *buf, int buflen)
{
char    buffer[256];
int     rval, i;
    if((rval = usb_control_msg(dev, USB_ENDPOINT_IN, USB_REQ_GET_DESCRIPTOR, (USB_DT_STRING << 8) + index, langid, buffer, sizeof(buffer), 1000)) < 0)
        return rval;
    if(buffer[1] != USB_DT_STRING)
        return 0;
    if((unsigned char)buffer[0] < rval)
        rval = (unsigned char)buffer[0];
    rval /= 2;
    /* lossy conversion to ISO Latin1 */
    for(i=1;i<rval;i++){
        if(i > buflen)  /* destination buffer overflow */
            break;
        buf[i-1] = buffer[2 * i];
        if(buffer[2 * i + 1] != 0)  /* outside of ISO Latin1 range */
            buf[i-1] = '?';
    }
    buf[i-1] = 0;
    return i-1;
}
#define USB_ERROR_NOTFOUND  1
#define USB_ERROR_ACCESS    2
#define USB_ERROR_IO        3
static int usbOpenDevice(usb_dev_handle **device, int vendor, char *vendorName, int product, char *productName)
{
struct usb_bus      *bus;
struct usb_device   *dev;
usb_dev_handle      *handle = NULL;
int                 errorCode = USB_ERROR_NOTFOUND;
static int          didUsbInit = 0;
    if(!didUsbInit){
        didUsbInit = 1;
        usb_init();
    }
    usb_find_busses();
    usb_find_devices();
    for(bus=usb_get_busses(); bus; bus=bus->next){
        for(dev=bus->devices; dev; dev=dev->next){
            if(dev->descriptor.idVendor == vendor && dev->descriptor.idProduct == product){
                char    string[256];
                int     len;
                handle = usb_open(dev); /* we need to open the device in order to query strings */
                if(!handle){
                    errorCode = USB_ERROR_ACCESS;
                    fprintf(stderr, "Warning: cannot open USB device: %s\n", usb_strerror());
                    continue;
                }
                if(vendorName == NULL && productName == NULL){  /* name does not matter */
                    break;
                }
                /* now check whether the names match: */
                len = usbGetStringAscii(handle, dev->descriptor.iManufacturer, 0x0409, string, sizeof(string));
                if(len < 0){
                    errorCode = USB_ERROR_IO;
                    fprintf(stderr, "Warning: cannot query manufacturer for device: %s\n", usb_strerror());
                }else{
                    errorCode = USB_ERROR_NOTFOUND;
                    /* fprintf(stderr, "seen device from vendor ->%s<-\n", string); */
                    if(strcmp(string, vendorName) == 0){
                        len = usbGetStringAscii(handle, dev->descriptor.iProduct, 0x0409, string, sizeof(string));
                        if(len < 0){
                            errorCode = USB_ERROR_IO;
                            fprintf(stderr, "Warning: cannot query product for device: %s\n", usb_strerror());
                        }else{
                            errorCode = USB_ERROR_NOTFOUND;
                            /* fprintf(stderr, "seen product ->%s<-\n", string); */
                            if(strcmp(string, productName) == 0)
                                break;
                        }
                    }
                }
                usb_close(handle);
                handle = NULL;
            }
        }
        if(handle)
            break;
    }
    if(handle != NULL){
        errorCode = 0;
        *device = handle;
    }
    return errorCode;
}

USB-2REL adalah modul driver 2-relay yang dapat dikendalikan oleh komputer melalui perantaraan port USB. Modul ini tidak membutuhkan catu daya eksternal sehingga sangat praktis untuk digunakan baik dengan komputer maupun laptop/netbook.
Modul USB-2REL (device) menggunakan V-USB, yakni open-source implementasi protokol USB kecepatan rendah untuk mikrokontroler AVR. Sedangkan pada komputer (host), program aplikasi pengontrolan modul USB-2REL dibuat menggunakan kompiler dan IDE C For Windows (freeware) yakni Pelles C. Untuk berkomunikasi dengan modul USB-2REL, program aplikasi menggunakan library libusb-win32 yang juga open-source.
Instalasi Driver Ketika modul USB-2REL dihubungkan ke komputer melalui port USB, maka sistem operasi Windows akan mendeteksi adanya piranti USB yang hadir di port USB. Selanjutnya, Windows akan melakukan proses enumerasi dengan tujuan untuk mengenali piranti USB yang baru hadir tersebut. Jika piranti USB tersebut dikenali, maka Windows akan menjalankan driver yang sesuai dan piranti USB pun siap digunakan.
Sesaat setelah modul USB-2REL terhubung ke port USB, maka mikrokontroler akan memperoleh suplai tegangan dan firmware di dalam memori program pun dijalankan. Firmware dalam mikrokontroler pun akan menjawab proses enumerasi yang dilakukan oleh Windows dengan menyetorkan ID-nya untuk dikenali oleh Windows.
Catatan: Modul USB-2REL menggunakan firmware implementasi USB buatan OBDEV (V-USB) dan telah banyak diimplementasikan oleh banyak perancang sistem mikrokontroler karena menyediakan ID yang gratis untuk digunakan. Oleh karenanya, jika port USB yang digunakan untuk modul USB-2REL pernah digunakan untuk modul USB lain seperti USBASP misalnya, maka filter libusb akan mengenali USB-2REL sebagai USBASP. Hal ini tidak menjadi masalah karena implementasi firmwarenya sama dan modul akan tetap beroperasi dengan baik sebagai driver relay.
Akan tetapi jika Windows tidak mengenali ID dari USB-2REL sebagai piranti USB yang telah terinstalasi pada port USB, maka Windows akan menampilkan dialog instalasi driver seperti screenshot berikut ini.

telinks_usb2rel_found

Modul USB-2REL dilengkapi dengan CD yang berisi installer Pelles C, source code project program aplikasi USB-2REL, dan driver libusb untuk USB-2REL.

telinks_usb2rel_driver

Setelah folder driver USB-2REL dipilih dan tekan OK serta Next >, maka proses instalasi driver pun dimulai.

telinks_usb2rel_installdriver

telinks_usb2rel_installed

Setelah instalasi driver selesai dan berhasil, maka USB-2REL kini siap digunakan. :)
Program Aplikasi USB-2REL

usb2rel_app1

Ketika program aplikasi USB-2REL dijalankan, sebelum form aplikasi ditampilkan, program melakukan inisialisasi dan mencoba berkomunikasi dengan driver USB-2REL yang telah aktif. Jika gagal maka program akan menampilkan pesan kesalahan bahwa modul USB-2REL tidak ditemukan dan program pun selesai.
Tapi jika program berhasil melakukan komunikasi dengan driver USB-2REL yang telah aktif, maka form aplikasi pun ditampilkan seperti gambar di samping ini.
Modul USB-2REL dapat diperintah atau diminta melakukan/mengerjakan fungsi tertentu sesuai dengan kode permintaan yang dikenalinya. Modul USB-2REL dapat diperintah untuk mengirimkan ID dari modul USB-2REL, yang dalam hal ini adalah data string “USB-2REL”. Pada program demo, Button Baca ID Modul akan mengirimkan permintaan tersebut kepada modul USB-2REL. Setelah ID Modul USB diterima, maka program akan menampilkannya pada editbox yang tersedia.

usb2rel_app2

Modul USB-2REL juga dapat diperintah untuk mengaktifkan/mematikan RELAY-1 dan RELAY-2, baik secara individu (sendiri-sendiri) ataupun secara bersamaan. Button ON dan Button OFF pada Group RELAY-1 berfungsi untuk mengaktifkan dan mematikan RELAY-1. Sedangkan Button ON dan Button OFF pada Group RELAY-2 berfungsi untuk mengaktifkan dan mematikan RELAY-2.
Button ALL RELAYS ON berfungsi untuk mengirimkan permintaan agar modul USB-2REL mengaktifkan kedua relay secara bersamaan. Dan Button ALL RELAYS OFF berfungsi untuk mengirimkan permintaan agar modul USB-2REL mematikan kedua relay secara bersamaan. Button EXIT, seperti nama yang diberikan kepadanya, berfungsi untuk keluar dari aplikasi.
Berikut adalah foto hasil pengujian modul USB-2REL dengan program aplikasi di atas.

usb2rel_onoff

Modul USB-2REL beserta dengan driver dan program aplikasinya telah kami uji pada beberapa komputer yang kami miliki, antara lain:

Netbook Lenovo @1.66GHz + Windows 7
PC Pentium-4 XEON @3.2GHz + Windows XP
PC Pentium-3 @750MHz + Windows XP
PC Pentium-2 @333MHz + Windows 98
Berikut adalah screenshot hasil pengujian pada sistem-sistem tersebut.

usb2rel_win7_640

usb2rel_winxp

usb2rel_win98_640

Berikut adalah screenshot program aplikasi kontrol USB-2REL yang dibuat menggunakan VB.NET 2005 Express Edition.

usb2rel_vbnet

0 komentar:

:a: :b: :c: :d: :e: :f: :g: :h: :i: :j: :k: :l: :m: :n:

Posting Komentar