投稿検索
生成AIの万年カレンダー
分類
47つれづれ日記アーカイブ
-
最新のタイトル
これなあに?
ChatGPTはコチラ。
Micro:bitがやって来た
SPI使用9bit転送のOLED接続
手元にあったMARY-OBというOLEDボード(2011)を整備が進んできたSPIドライバー
経由で接続することにチャレンジしたので、まとめておく。
SPIドライバーは当初、GPIOが26ピンだったためSPIがバス1本のStandardSPIのみの
サポートで、基本的に8bit単位の転送しかできなかった。
40ピンの時代になってBCM2835が搭載され、拡張SPIへの本格的取組が行われてきた。
カーネルが4.4.13以降、何回かの錯誤を経て、SPIバス2本が使える形に仕上がって
来ている。
拡張されたauxiliary SPI側では、LoSSIやワードサイズの指定が(限定的に)できる。
詳細は、ここを参照するとよい。
【準備】
1.BCM2835が載ったRaspberryPiを用意する。
2.カーネル4.4.y(又は4.9.y)のRaspbianOSを
インストールして起動する。
3.「 ls /dev/spi*」コマンドで、
/dev/spidev0.0 /dev/spidev0.1 /dev/spidev1.0 /dev/spidev1.1
の4ポートが出現するように設定する。そのためには、
・config.txtに
dtoverlay=pi3-disable-bt
dtoverlay=spi1-2cs
を追加する。 (注意:/dev/ttyS0との共存はできない)
・/boot/cmdline.txtに
console=ttyS0,115200
があれば、この部分を削除する。
4.pigpioライブラリーをインストールする。
http://abyz.co.uk/rpi/pigpio/download.html (ガイド付き)
または、いつもの、
sudo apt-get install pigpio python-pigpio python3-pigpio
5.環境をテストする(make -j4を実施した時)。
sudo ./x_pigpio
【OLEDサンプルプログラム】
OLEDユニット UG-2828GDEDF11 に使われているコントローラーは、
SOLOMON SYSTECH社のSSD1351でした。
SPIのピンヘッダの利用は次の通り。
GPIO16をVCC_POWER_ONに利用している。焼き付き防止に有効。 |
| SPIバスのオープン | |
| int spiOpen(unsigned spiChan, unsigned baud, unsigned spiFlags); | |
| spiChanでチップセレクトの出力先を、baudにはクロックスピードを設定する。 | |
| spiFlagsの意味 | |
| spiFlagsは下位22ビットが次のように定義されている。 | |
| 21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 | |
| b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m |
このサンプルでは、次のようにオープンしている。
static uint16_t mode = 0x160;
Aをオンにし、auxSPIを使用する。
u0,u1をオンにし、二つのポートCE0,1の制御をライブラリに委ねている。
static uint16_t bits = 9;
bits of word は9ビットを指定
static uint32_t speed = 10000000;
speedはPiZeroやPi3に合わせて要求した。P12は倍でもOK。実速度は異なる。
spiOpen(0, speed, bits<<16 | mode );
/dev/spidev1.0 のオープン
ソースファイル
//=========================================================
// File Name : oledspi2.c
// Function : OLED Control
//---------------------------------------------------------
//---------------------------------------------------------
// Copyright (C) 2010-2011 Munetomo Maruyama
//=========================================================
// ---- License Information -------------------------------
// Anyone can FREELY use this code fully or partially
// under conditions shown below.
// 1. You may use this code only for individual purpose,
// and educational purpose.
// Do not use this code for business even if partially.
// 2. You can copy, modify and distribute this code.
// 3. You should remain this header text in your codes
// including Copyright credit and License Information.
// 4. Your codes should inherit this license information.
//=========================================================
// ---- Patent Notice -------------------------------------
// I have not cared whether this system (hw + sw) causes
// infringement on the patent, copyright, trademark,
// or trade secret rights of others. You have all
// responsibilities for determining if your designs
// and products infringe on the intellectual property
// rights of others, when you use technical information
// included in this system for your business.
//=========================================================
// ---- Disclaimers ---------------------------------------
// The function and reliability of this system are not
// guaranteed. They may cause any damages to loss of
// properties, data, money, profits, life, or business.
// By adopting this system even partially, you assume
// all responsibility for its use.
//=========================================================
#include <stdio.h>
#include <inttypes.h>
#include <pigpio.h>
#include "oled.h"
#include "font.h"
//=================
// Font Parameters
//=================
#define OLED_FONT_XSIZE 8
#define OLED_FONT_YSIZE 8
//======================
// Define OLED Commands
//======================
#define OLED_COMMAND 1
#define OLED_DATA 2
//
#define C_SET_COLUMN_ADDRESS 0x0215
#define C_SET_ROW_ADDRESS 0x0275
#define D_START_ADDRESS 2
#define D_END_ADDRESS 3
//
#define C_WRITE_RAM_COMMAND 0x005c
#define C_READ_RAM_COMMAND 0x005d
//
#define C_SET_REMAP_COLOR_DEPTH 0x01a0
#define D_SET_REMAP_COLOR_DEPTH 2
//
#define C_SET_DISPLAY_START_LINE 0x01a1
#define D_SET_DISPLAY_START_LINE 2
//
#define C_SET_DISPLAY_OFFSET 0x01a2
#define D_SET_DISPLAY_OFFSET 2
//
#define C_SET_DISPLAY_MODE_ALL_OFF 0x00a4
#define C_SET_DISPLAY_MODE_ALL_ON 0x00a5
#define C_SET_DISPLAY_MODE_RESET 0x00a6
#define C_SET_DISPLAY_MODE_INVERSE 0x00a7
//
#define C_FUNCTION_SELECTION 0x01ab
#define D_FUNCTION_SELECTION 2
//
#define C_SET_SLEEP_MODE_ON 0x00ae
#define C_SET_SLEEP_MODE_OFF 0x00af
//
#define C_SET_RESET_PRECHARGE_PERIOD 0x01b1
#define D_SET_RESET_PRECHARGE_PERIOD 2
//
#define C_ENHANCE_DRIVING_SCHEME_CAPABILITY 0x03b2
#define D_ENHANCE_DRIVING_SCHEME_CAPABILITY_1 2
#define D_ENHANCE_DRIVING_SCHEME_CAPABILITY_2 3
#define D_ENHANCE_DRIVING_SCHEME_CAPABILITY_3 4
//
#define C_FRONT_CLOCK_DRIVER_OSCILLATOR_FREQUENCY 0x01b3
#define D_FRONT_CLOCK_DRIVER_OSCILLATOR_FREQUENCY 2
//
#define C_SET_SEGMENT_LOW_VOLTAGE 0x03b4
#define D_SET_SEGMENT_LOW_VOLTAGE_1 2 // 0xa0 or 0xa2
#define D_SET_SEGMENT_LOW_VOLTAGE_2 3 // 0xb5
#define D_SET_SEGMENT_LOW_VOLTAGE_3 4 // 0x55
//
#define C_SET_GPIO 0x01b5
#define D_SET_GPIO 2
//
#define C_SET_SECOND_PRECHARGE_PERIOD 0x01b6
#define D_SET_SECOND_PRECHARGE_PERIOD 2
//
#define C_LOOKUP_TABLE_FOR_GRAY_SCALE_PULSE_WIDTH 0x3fb8
static const uint8_t GAMMA_TABLE[63] =
{
0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09,
0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11,
//
0x12, 0x13, 0x15, 0x17, 0x19, 0x1b, 0x1d, 0x1f,
0x21, 0x23, 0x25, 0x27, 0x2a, 0x2d, 0x30, 0x33,
//
0x36, 0x39, 0x3c, 0x3f, 0x42, 0x45, 0x48, 0x4c,
0x50, 0x54, 0x58, 0x5c, 0x60, 0x64, 0x68, 0x6c,
//
0x70, 0x74, 0x78, 0x7d, 0x82, 0x87, 0x8c, 0x91,
0x96, 0x9b, 0xa0, 0xa5, 0xaa, 0xaf, 0xb4
};
//
#define C_USE_BUILT_IN_LINEAR_LUT 0x00b9
//
#define C_SET_PRECHARGE_VOLTAGE 0x01bb
#define D_SET_PRECHARGE_VOLTAGE 2
//
#define C_SET_VCOMH_VOLTAGE 0x01be
#define D_SET_VCOMH_VOLTAGE 2
//
#define C_SET_CONTRAST_CURRENT_FOR_COLOR_ABC 0x03c1
#define D_SET_CONTRAST_CURRENT_FOR_COLOR_A 2
#define D_SET_CONTRAST_CURRENT_FOR_COLOR_B 3
#define D_SET_CONTRAST_CURRENT_FOR_COLOR_C 4
//
#define C_MASTER_CONTRAST_CURRENT_CONTROL 0x01c7
#define D_MASTER_CONTRAST_CURRENT_CONTROL 2
//
#define C_SET_MUX_RATIO 0x01ca
#define D_SET_MUX_RATIO 2
//
#define C_SET_COMMAND_LOCK 0x01fd
#define D_SET_COMMAND_LOCK 2
//
#define C_HORIZONTAL_SCROLL 0x0596
#define D_HORIZONTAL_SCROLL_A 2
#define D_HORIZONTAL_SCROLL_B 3
#define D_HORIZONTAL_SCROLL_C 4
#define D_HORIZONTAL_SCROLL_D 5
#define D_HORIZONTAL_SCROLL_E 6
//
#define C_STOP_MOVING 0x009e
#define C_START_MOVING 0x009f
#define MAX_WORKBUF 64
uint8_t *xvsnprintf(uint8_t *str, int32_t length, const char *format)
{
uint8_t *ptr;
ptr = (uint8_t*) format;
while(*ptr != '\0')
{
if (length > 0) {*str++ = *ptr; length--;}
ptr++;
}
//
if (str != NULL) *str = '\0';
return str;
}
#
//=============
// Globals
//=============
volatile uint32_t gOLED_printf_Font = OLED_FONT_SMALL;
volatile uint32_t gOLED_printf_ColorF = OLED_WHT;
volatile uint32_t gOLED_printf_ColorB = OLED_BLK;
volatile uint32_t gOLED_printf_PosX = 0;
volatile uint32_t gOLED_printf_PosY = 0;
//
volatile uint32_t gOELD_Orientation_Mode = OLED_TOP_N;
static uint16_t mode = 0x160; /* SPI1,u1,u0 */
static uint16_t bits = 9;
static uint32_t speed = 10000000;
uint32_t oled[65];
//======================
// Initialize OLED
//======================
/*
int gpioSetMode(unsigned gpio, unsigned mode);
int gpioGetMode(unsigned gpio);
int gpioSetPullUpDown(unsigned gpio, unsigned pud);
int gpioRead(unsigned gpio);
int gpioWrite(unsigned gpio, unsigned level);
int gpioTrigger(unsigned user_gpio, unsigned pulseLen, unsigned level);
int spiRead(unsigned handle, char *buf, unsigned count);
int spiWrite(unsigned handle, char *buf, unsigned count);
int spiXfer(unsigned handle, char *txBuf, char *rxBuf, unsigned count);
*/
int Init_OLED(void)
{
uint32_t i;
// Display OFF
oled[OLED_COMMAND] = C_SET_DISPLAY_MODE_ALL_OFF;
OLED_Send_Command(oled);
//
// Initialization Sequence of OLED
//
oled[OLED_COMMAND] = C_SET_COMMAND_LOCK;
oled[D_SET_COMMAND_LOCK] = 0x112; // unlock
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_COMMAND_LOCK;
oled[D_SET_COMMAND_LOCK] = 0x1b1; // unlock
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_SLEEP_MODE_ON;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_FRONT_CLOCK_DRIVER_OSCILLATOR_FREQUENCY;
oled[D_FRONT_CLOCK_DRIVER_OSCILLATOR_FREQUENCY] = 0xf1;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_MUX_RATIO;
oled[D_SET_MUX_RATIO] = 0x17f;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_DISPLAY_OFFSET;
oled[D_SET_DISPLAY_OFFSET] = 0x100;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_DISPLAY_START_LINE;
oled[D_SET_DISPLAY_START_LINE] = 0x100;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_REMAP_COLOR_DEPTH;
oled[D_SET_REMAP_COLOR_DEPTH] = 0x174; // 64k colors
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_GPIO;
oled[D_SET_GPIO] = 0x100;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_FUNCTION_SELECTION;
oled[D_FUNCTION_SELECTION] = 0x101;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_SEGMENT_LOW_VOLTAGE;
oled[D_SET_SEGMENT_LOW_VOLTAGE_1] = 0x1a0; // use external VSL
oled[D_SET_SEGMENT_LOW_VOLTAGE_2] = 0x1b5;
oled[D_SET_SEGMENT_LOW_VOLTAGE_3] = 0x155;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_CONTRAST_CURRENT_FOR_COLOR_ABC;
oled[D_SET_CONTRAST_CURRENT_FOR_COLOR_A] = 0x1c8;
oled[D_SET_CONTRAST_CURRENT_FOR_COLOR_B] = 0x180;
oled[D_SET_CONTRAST_CURRENT_FOR_COLOR_C] = 0x1c8;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_MASTER_CONTRAST_CURRENT_CONTROL;
oled[D_MASTER_CONTRAST_CURRENT_CONTROL] = 0x10f;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_LOOKUP_TABLE_FOR_GRAY_SCALE_PULSE_WIDTH;
for (i = 2; i < 65; i++)
{
oled[i] = (uint32_t) GAMMA_TABLE[i - 2] | 0x100;
}
OLED_Send_Command(oled);
//
//oled[OLED_COMMAND] = C_USE_BUILT_IN_LINEAR_LUT;
//OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_RESET_PRECHARGE_PERIOD;
oled[D_SET_RESET_PRECHARGE_PERIOD] = 0x132;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_ENHANCE_DRIVING_SCHEME_CAPABILITY;
oled[D_ENHANCE_DRIVING_SCHEME_CAPABILITY_1] = 0x1a4;
oled[D_ENHANCE_DRIVING_SCHEME_CAPABILITY_2] = 0x100;
oled[D_ENHANCE_DRIVING_SCHEME_CAPABILITY_3] = 0x100;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_PRECHARGE_VOLTAGE;
oled[D_SET_PRECHARGE_VOLTAGE] = 0x117;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_SECOND_PRECHARGE_PERIOD;
oled[D_SET_SECOND_PRECHARGE_PERIOD] = 0x101;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_VCOMH_VOLTAGE;
oled[D_SET_VCOMH_VOLTAGE] = 0x105;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_DISPLAY_MODE_RESET;
OLED_Send_Command(oled);
//
// Clear Screen
oled[OLED_COMMAND] = C_SET_COLUMN_ADDRESS;
oled[D_START_ADDRESS] = 0x100;
oled[D_END_ADDRESS] = 0x17f;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_ROW_ADDRESS;
oled[D_START_ADDRESS] = 0x100;
oled[D_END_ADDRESS] = 0x17f;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_WRITE_RAM_COMMAND;
OLED_Send_Command(oled);
//
}
//==================================
// Initialize OLED with Orientation
//==================================
void Init_OLED_with_Orientation(uint32_t mode)
{
uint8_t command;
Init_OLED();
gOELD_Orientation_Mode = mode;
//
command = (mode == OLED_TOP_W)? 0x25 :
(mode == OLED_TOP_S)? 0x26 :
(mode == OLED_TOP_E)? 0x37 : 0x34;
oled[OLED_COMMAND] = C_SET_REMAP_COLOR_DEPTH;
oled[D_SET_REMAP_COLOR_DEPTH] = command | 0x100;
OLED_Send_Command(oled);
}
//=====================
// OLED Send Command
//=====================
void OLED_Send_Command(uint32_t *oled)
{
uint32_t i;
uint32_t count,countR;
uint16_t bus;
count = (oled[OLED_COMMAND] >> 8) & 0x0ff;
bus = oled[OLED_COMMAND] & 0xFF;
for (i=0;i<=count;i++) {
countR = spiWrite( oled[0], (char *)&bus, 2);
bus = oled[OLED_DATA+i] | 0x100;
}
//
}
//=====================
// OLED Send Data
//=====================
void OLED_Send_Data(uint32_t *oled, int count)
{
uint32_t i;
uint16_t bus;
for (i=0;i<count;i++) {
bus = (oled[OLED_DATA+i] & 0xff) | 0x100;
spiWrite( oled[0], (char *)&bus, 2);
}
}
//====================
// OLED Send a Pixel
//====================
void OLED_Send_Pixel(uint32_t color)
{
oled[OLED_DATA+0] = (color >> 8) ;
oled[OLED_DATA+1] = color;
OLED_Send_Data(oled, 2);
}
//===================
// OLED Clear Screen
//===================
void OLED_Clear_Screen(uint32_t color)
{
uint32_t i;
uint32_t bus;
oled[OLED_COMMAND] = C_WRITE_RAM_COMMAND;
OLED_Send_Command(oled);
bus = (color & 0xff00)<<8 | (color & 0xff) | 0x01000100;
for (i=0;i<128*128;i++) {
spiWrite( oled[0], (char *)&bus, 4);
}
}
//=======================
// OLED Draw a Character
//=======================
// scale should be 0, 1 or 2
void OLED_Draw_Char(char ch, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b, uint32_t scale)
{
uint32_t x0, y0;
uint32_t xsize, ysize;
uint32_t x, y;
uint32_t xfont, yfont;
uint32_t pixel;
uint32_t color;
//
uint32_t col0, col1, row0, row1;
ch = (ch < 0x20)? 0x20 : (ch > 0x7f)? 0x7f : ch;
//
x0 = posx * (OLED_FONT_XSIZE << scale);
y0 = posy * (OLED_FONT_YSIZE << scale);
//
xsize = OLED_FONT_XSIZE * (1 << scale);
ysize = OLED_FONT_YSIZE * (1 << scale);
//
if ((x0 <= (128 - xsize)) && (y0 <= (128 - ysize)))
{
col0 = (gOELD_Orientation_Mode == OLED_TOP_W)? y0 :
(gOELD_Orientation_Mode == OLED_TOP_S)? x0 :
(gOELD_Orientation_Mode == OLED_TOP_E)? y0 : x0;
col1 = (gOELD_Orientation_Mode == OLED_TOP_W)? y0 + ysize - 1 :
(gOELD_Orientation_Mode == OLED_TOP_S)? x0 + xsize - 1 :
(gOELD_Orientation_Mode == OLED_TOP_E)? y0 + ysize - 1 : x0 + xsize - 1;
row0 = (gOELD_Orientation_Mode == OLED_TOP_W)? x0 :
(gOELD_Orientation_Mode == OLED_TOP_S)? y0 :
(gOELD_Orientation_Mode == OLED_TOP_E)? x0 : y0;
row1 = (gOELD_Orientation_Mode == OLED_TOP_W)? x0 + xsize - 1 :
(gOELD_Orientation_Mode == OLED_TOP_S)? y0 + ysize - 1 :
(gOELD_Orientation_Mode == OLED_TOP_E)? x0 + xsize - 1 : y0 + ysize - 1;
//
oled[OLED_COMMAND] = C_SET_COLUMN_ADDRESS;
oled[D_START_ADDRESS] = (col0 > 127)? 127 : col0;
oled[D_END_ADDRESS] = (col1 > 127)? 127 : col1;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_SET_ROW_ADDRESS;
oled[D_START_ADDRESS] = (row0 > 127)? 127 : row0;
oled[D_END_ADDRESS] = (row1 > 127)? 127 : row1;
OLED_Send_Command(oled);
//
oled[OLED_COMMAND] = C_WRITE_RAM_COMMAND;
OLED_Send_Command(oled);
//
for (y = 0; y < ysize; y++)
{
for (x = 0; x < xsize; x++)
{
xfont = x >> scale;
yfont = y >> scale;
pixel = FONT[((uint32_t) ch - 0x20) * 8 + yfont];
pixel = (pixel >> (OLED_FONT_XSIZE - 1 - xfont)) & 0x01;
color = (pixel == 1)? color_f : color_b;
OLED_Send_Pixel(color);
}
}
}
}
//====================
// OLED Make Color
//====================
// RGB num
// BLK 000 0000-003f (< 64)
// BLU 001 0040-007f (<128)
// CYN 011 0080-00bf (<192)
// GRN 010 00c0-00ff (<256)
// YEL 110 0100-013f (<320)
// WHT 111 0140-017f (<384)
// MAG 101 0180-01bf (<448)
// RED 100 01c0-01ff (<512)
// BLK 000
//===========================
// OLED Set printf() Position
//===========================
void OLED_printf_Position(uint32_t posx, uint32_t posy)
{
gOLED_printf_PosX = posx;
gOLED_printf_PosY = posy;
}
//=====================
// OLED printf
//=====================
void OLED_printf(const char *format, ...)
{
uint8_t buf[256];
uint8_t *pStr;
xvsnprintf(buf, 256, format);
pStr = buf;
while(*pStr != '\0')
{
if (*pStr == '\n')
{
gOLED_printf_PosX = 0;
gOLED_printf_PosY++;
}
else
{
OLED_Draw_Char(*pStr, gOLED_printf_PosX, gOLED_printf_PosY,
gOLED_printf_ColorF, gOLED_printf_ColorB, gOLED_printf_Font);
gOLED_printf_PosX++;
}
pStr++;
//
if (gOLED_printf_PosX >= (128 / (OLED_FONT_XSIZE << gOLED_printf_Font)))
{
gOLED_printf_PosX = 0;
gOLED_printf_PosY++;
}
if (gOLED_printf_PosY >= (128 / (OLED_FONT_YSIZE << gOLED_printf_Font)))
{
gOLED_printf_PosY = 0;
}
}
}
//=====================
// Display BITMAP
//=====================
//-----------------------
// Main Routine
//-----------------------
#define BMP 1 // select which BMP you want to see.
#define BUD 30 // select which BUD part you want to see.
#include "../bmp/lego8.bmp.plt.h"
#include "../bmp/lego8.bmp.rgb.h"
#include "../bmp/nana8.bmp.plt.h"
#include "../bmp/nana8.bmp.rgb.h"
int main() {
uint32_t x, y, i;
uint8_t index, orien;
uint32_t palette;
uint32_t red, blu, grn;
uint32_t oled1, oled2, pixel;
if (gpioInitialise() < 0) return -1;
gpioSetMode(16,1);
gpioSetMode(23,1);
gpioWrite(16,1); // OLED Vcc PowerON
time_sleep( 0.1 ); // wait for 100ms
// OLED Reset
// OLED_/RES GPIO OUT
gpioWrite(23,0);
time_sleep( 0.1 ); // wait for 100ms
gpioWrite(23,1); // high (reset)
time_sleep( 0.1 ); // wait for 100ms
// Initialize Hardware
oled1 = spiOpen(0, speed, bits<<16 | mode );
oled2 = spiOpen(1, speed, bits<<16 | mode );
for (orien=100; orien>0; orien--) {
// Initialization
//
oled[0] = oled1;
Init_OLED_with_Orientation(orien & 3);
OLED_Clear_Screen(OLED_BLK) ;
//
// Send Bitmap Data1
//
i = 0;
for (y = 0; y < 128; y++)
{
for (x = 0; x < 128; x++)
{
index = BMP_RGB[i++];
palette = BMP_PLT[index];
red = (palette >> (16 + 3)) & 0x01f;
grn = (palette >> ( 8 + 2)) & 0x03f;
blu = (palette >> ( 0 + 3)) & 0x01f;
pixel = (red << 11) + (grn << 5) + (blu << 0);
OLED_Send_Pixel(pixel);
}
}
// Display ON
oled[OLED_COMMAND] = C_SET_SLEEP_MODE_OFF;
OLED_Send_Command(oled);
// Dummy Print (to make correct link)
OLED_printf_Position(0, 0);
OLED_printf("RaspberryPi");
//
// Send Bitmap Data2
//
time_sleep( 1 ); // wait for 1s
}
gpioWrite(16,0); // OLED Vcc PowerOFF
spiClose(oled1);
spiClose(oled2);
gpioTerminate();
}
//=========================================================
// End of Program
//=========================================================
oled.h
ifndef __OLED_H__
#define __OLED_H__
//===============
// Define Colors
//===============
#define OLED_RED_MAX 0x1f
#define OLED_GRN_MAX 0x3f
#define OLED_BLU_MAX 0x1f
#define OLED_RED_MIN 0x00
#define OLED_GRN_MIN 0x00
#define OLED_BLU_MIN 0x00
#define OLED_RED_MID 0x10
#define OLED_GRN_MID 0x20
#define OLED_BLU_MID 0x10
//
#define OLED_RED ((OLED_RED_MAX << 11) + (OLED_GRN_MIN << 5) + (OLED_BLU_MIN << 0))
#define OLED_GRN ((OLED_RED_MIN << 11) + (OLED_GRN_MAX << 5) + (OLED_BLU_MIN << 0))
#define OLED_BLU ((OLED_RED_MIN << 11) + (OLED_GRN_MIN << 5) + (OLED_BLU_MAX << 0))
#define OLED_BLK ((OLED_RED_MIN << 11) + (OLED_GRN_MIN << 5) + (OLED_BLU_MIN << 0))
#define OLED_WHT ((OLED_RED_MAX << 11) + (OLED_GRN_MAX << 5) + (OLED_BLU_MAX << 0))
#define OLED_YEL ((OLED_RED_MAX << 11) + (OLED_GRN_MAX << 5) + (OLED_BLU_MIN << 0))
#define OLED_CYN ((OLED_RED_MIN << 11) + (OLED_GRN_MAX << 5) + (OLED_BLU_MAX << 0))
#define OLED_MAG ((OLED_RED_MAX << 11) + (OLED_GRN_MIN << 5) + (OLED_BLU_MAX << 0))
#define OLED_GRY ((OLED_RED_MID << 11) + (OLED_GRN_MID << 5) + (OLED_BLU_MID << 0))
//=================
// Font Parameters
//=================
#define OLED_FONT_SMALL 0
#define OLED_FONT_MEDIUM 1
#define OLED_FONT_LARGE 2
//=================
// Orientation Mode
//=================
enum OELD_ORIENTATION_MODE {OLED_TOP_N, OLED_TOP_W, OLED_TOP_S, OLED_TOP_E};
//==============
// Prototypes
//==============
int Init_OLED(void);
void Init_OLED_with_Orientation(uint32_t mode);
void OLED_Send_Command(uint32_t *oled);
void OLED_Send_Pixel(uint32_t color);
uint32_t OLED_Draw_Text_Small(char *pStr, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b);
uint32_t OLED_Draw_Text_Medium(char *pStr, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b);
uint32_t OLED_Draw_Text_Large(char *pStr, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b);
void OLED_Draw_Char(char ch, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b, uint32_t scale);
void OLED_Draw_Dot(int32_t x, int32_t y, int32_t size, uint32_t color);
void OLED_Clear_Screen(uint32_t color);
void OLED_Fill_Rect(int32_t x0, int32_t y0, int32_t xsize, int32_t ysize, uint32_t color);
char OLED_Num4_to_Char(uint32_t num4);
uint32_t OLED_Draw_Hex(uint32_t bitlen, uint32_t hex, uint32_t posx, uint32_t posy, uint32_t color_f, uint32_t color_b);
uint32_t OLED_Make_Color(uint32_t num);
//
void OLED_printf_Font(uint32_t font);
void OLED_printf_Color(uint32_t color_f, uint32_t color_b); // corrected 2011.03.20 MM
void OLED_printf_Position(uint32_t posx, uint32_t posy);
void OLED_printf(const char *format, ...);
#endif // __OLED_H__
カテゴリー: RaspberryPi
コメントする
WiringPi-Python最新対応
WiringPiはPi2として最新化されているが、Python対応はメンテが止まったように
見えて困っていた。
次のUpdateによるインストールで、4.4系や4.9系のPython,Python3 共に対応できた
のでまとめておく。
1)Raspbianの、この時点の最新バイナリをダウンロードしインストールする。
https://downloads.raspberrypi.org/raspbian_latest
2)4.9系にUPしたい人は、次を実施する。
sudo rpi-update
sudo reboot
3)sudo apt-get update;sudo apt-get upgrade -y
4)sudo apt-get install -y python-dev python-setuptools swig
5)WiringPiのPython wrapper をダウンロードする。
git clone https://github.com/Gadgetoid/WiringPi2-Python.git
cd WiringPi2-Python
6)WiringPi部分を最新化する。
wget -O wiring.tar.gz https://git.drogon.net/?p=wiringPi;a=snapshot;h=96344ff7125182989f98d3be8d111952a8f74e15;sf=tgz
(?とp=は空けないこと)
tar xzf *.gz
cp -r wiringPi*/* WiringPi
7)setup.py の Extension の途中に次の行を追加
extra_link_args=[‘-lrt’,’-lcrypt’],
8)不要ファイルの削除
WiringPi/devLib 配下の不要な piFaceOld.c を削除
9)wiringpi.i の398行目の修正
PyString_FromStringAndSize( ⇒ PyUnicode_FromStringAndSize(
10)./build.sh で最終インストール
build.sh はPython とPyhton3 を同時にインストールできるように編集
swig2.0 -python -threads wiringpi.i sudo python setup.py build install sudo python3 setup.py build install sudo python test.py sudo python3 test.py
カテゴリー: RaspberryPi
1件のコメント
【訃報】水野さん
47東京白堊会 各位
こんばんは。
悲しいお知らせですが、同期5組だった水野(藤原)明美さんが7月25日に
ご入院中の病院にてご逝去されました。
肺に転移して、息苦しいと感じ受診したら、原発は乳がんで最終ステージ
だったとのことです。
ご家族から、次のとおりご葬儀のお知らせをいただきましたので、
お知らせ申し上げます。
通夜式 7月27日(水) 18時~
告別式 7月28日(木) 12時
場所 さがみ典礼・土浦ホール 〒300-0048 茨城県土浦市田中1-6-9
℡:029-823-4999 (JR常磐線土浦駅から車で7分)
PiZeroでUSB接続インターネット
USBドライバーとDNSサーバーの設定でつまづいたので、ノウハウをメモ。
1)最新Jessieをダウンロードし、マイクロSDを作る。
2)Windows上で、config.txt file に dtoverlay=dwc2 を行追加し、保存する。
3)Windows上で、cmdline.txt file の rootwait の後ろに modules-load=dwc2,g_ether を追記し、保存する。
4)これで一旦、コンソール環境のある構成にて、SDからRaspbianOSを立ち上げ、
次の設定をする。
5)/etc/network/interfacesに次を書き込む。
allow-hotplug usb0 iface usb0 inet static address 192.168.137.2 netmask 255.255.255.0 wpa-conf /etc/wpa_supplicant/wpa_supplicant.conf dns-nameservers 192.168.1.1
6)SDメモリカードをPiZeroに入れ、マイクロUSBケーブルをPCに接続する。
PowerUSBではなく内側のUSB端子です。
7)PCのデバイスマネージャーで、ポートCOMnにシリアルIOとして現れたら、
そのドライバを、このモジュールで更新する。
8)デバイスマネージャーのネットワークアダプターのところに、
USB Ethernet/RNDIS Gadget が現れることを確認する。
9)コントロールパネルのネットワーク接続のところにイーサネットとして、
新しい接続が現れることを確認する。
10)「新しい接続のプロパティ」の「プロトコルバージョン4プロパティ」に
IPアドレスが 192.168.137.1 と設定されることを確認。違っていれば
修正する。
11)メイン接続のプロパティの共有タブで、共有を許可し、許可プロトコルを
確認・設定する。LANのアドレスが、137に変わるという警告は無視する。
12)PiZeroを再起動する。
これで、PiZeroからインターネットにUSB経由で出ることができる。
カテゴリー: RaspberryPi
1件のコメント
Arduinoで、LCD日本語表示
ArduinoMEGA用のスケッチができたので、メモしておきます。
【追記】漢字ROM判断や縦横切替、スクロールなどの機能追加
実際の表示例は、こんな風になります。
追加ライブラリ:
Adafruit_TFTLCD
Adafruit_GFX
fontx TFTKanji
fontR ここ・漢字ROM無しなら、SD内のフォントfileを使う
追加フォント:
VMNL12.lzh http://homepage3.nifty.com/silo/FONTV/
漢字ROM スイッチサイエンス
入力データ中の特殊コード:
\n 改行
\a この行をSDへ追加保存
\c 色を変更する(次が0~7)
\d 保存ファイル削除
\f 表示データを保存ファイルからとする
\s スクリーンクリア
\1~4 倍角表示
\6~9 画面回転(0~3)、0,2はスクロールモード
// IMPORTANT: Adafruit_TFTLCD LIBRARY MUST BE SPECIFICALLY
// CONFIGURED FOR EITHER THE TFT SHIELD OR THE BREAKOUT BOARD.
// SEE RELEVANT COMMENTS IN Adafruit_TFTLCD.h FOR SETUP.
//Technical support:goodtft@163.com
// SDカード用ライブラリ
#include <SD.h>
#include <SPI.h>
// FONTライブラリ
#include <fontR.h>
#include <fontx.h>
// 漢字パターン格納用
unsigned char matrixdata32[32]; //16×16用表示データ
unsigned char matrixdata16[16]; //16× 8用表示データ
int s; //a font memory size
#include <Adafruit_GFX.h> // Core graphics library
#include <Adafruit_TFTLCD.h> // Hardware-specific library
// The control pins for the LCD can be assigned to any digital or
// analog pins...but we'll use the analog pins as this allows us to
// double up the pins with the touch screen (see the TFT paint example).
#define LCD_CS A3 // Chip Select goes to Analog 3
#define LCD_CD A2 // Command/Data goes to Analog 2
#define LCD_WR A1 // LCD Write goes to Analog 1
#define LCD_RD A0 // LCD Read goes to Analog 0
#define LCD_RESET A4 // Can alternately just connect to Arduino's reset pin
// Assign human-readable names to some common 16-bit color values:
#define BLACK 0x0000
#define BLUE 0x001F
#define RED 0xF800
#define GREEN 0x07E0
#define CYAN 0x07FF
#define MAGENTA 0xF81F
#define YELLOW 0xFFE0
#define WHITE 0xFFFF
Adafruit_TFTLCD tft(LCD_CS, LCD_CD, LCD_WR, LCD_RD, LCD_RESET);
// If using the shield, all control and data lines are fixed, and
// a simpler declaration can optionally be used:
// Adafruit_TFTLCD tft;
int16_t x = 0; int16_t y = 0;
File dispF;
uint8_t size = 2, xsize = size, yf = 0, ROM = 1;
uint16_t color = WHITE, bg = BLUE;
uint16_t palette[8] = {BLACK,BLUE,RED,GREEN,CYAN,MAGENTA,YELLOW,WHITE};
char input[12] = "dispMsg.txt";
void setup(void) {
// ROMの初期化 53,51,50,52
// Unoでは、10,11,12,13
pinMode (SS, OUTPUT);
Serial.begin(115200);
/*SPI通信の設定*/
SPI.begin ();
SPI.setBitOrder(MSBFIRST);
SPI.setDataMode(3);
SPI.setClockDivider(SPI_CLOCK_DIV16);
Serial.println(F("TFT LCD Kanji test"));
readFontASCII(0x70, 260048);
if (matrixdata16[8]==0) {
ROM = 0;
Serial.println(F("SD Font is used"));
}
Serial.println(F("Using Adafruit 3.5\" TFT Mega Board Pinout"));
Serial.print("TFT size is "); Serial.print(tft.width());
Serial.print("x"); Serial.println(tft.height());
tft.reset();
uint16_t identifier = tft.readID();
if (identifier == 0x9481) {
Serial.println(F("Found ILI9481 LCD driver"));
}
else {
Serial.print(F("Unknown LCD driver chip: "));
Serial.println(identifier, HEX);
return;
}
// SDカードの初期化 35,51,50,52
if (!SD.begin(35)) { // Unoでは、 9,11,12,13
Serial.println(F("SD card error !"));
return;
}
tft.begin(identifier);
tft.setRotation(3);
tft.fillScreen(BLUE);
tft.setCursor(0, 0);
// 準備ができたら「準備完了!」と送信。
// ArduinoIDEはShift_JISなのでエスケープ文字をつけて文字コードを送信する。
Serial.print("Arduino,\x8F\x80 \x94\xF5 \x8A\xAE \x97\xB9 \x81\x49\n");
// if (SD.exists(input)) dispF = SD.open(input);
}
void loop(void) {
int ix=16, iy=16, p=32, ixb;
// 文字コード格納用
static unsigned int kanji;
// 受信データが届くまで待つ
if (!dispF) while (!Serial.available());
else if (!dispF.available()) {
dispF.close();
return;
}
// 文字コードを検知して1バイト文字なら1バイトだけ抜き出し、
// 2バイト文字なら2バイトをくっつける
if (dispF)
kanji = (unsigned int)dispF.read() << 8;
else kanji = (unsigned int)Serial.read() << 8;
if ((kanji >= 0x8000 && kanji <= 0xA000) || kanji >= 0xE000) {
if (!dispF) {
while (!Serial.available());
kanji |= Serial.read();
} else kanji |= dispF.read();
xsize = size; // 全角ピッチ
// パターン取得
if (ROM) showSJIS2byte(kanji) ;
// sendDotsToSerial32();
} else { // 半角
kanji >>= 8;
if (kanji == 0x5C) {
int peek,c;
if (!dispF) {
while (!Serial.available());
peek = Serial.peek();
} else peek = dispF.read();
if (peek == 0x6E) { // \n 改行
if (!dispF) {
Serial.read();
}
x = 1000; // 強制改行
return;
} else if (peek== 0x61) { // \a ファイル追記
Serial.println("File creation and addition");
Serial.read();
dispF = SD.open(input, FILE_WRITE);
while(Serial.available()) dispF.write(Serial.read());
dispF.close();
return;
} else if (peek== 0x63) { // \c 色変更
if (!dispF) {
Serial.read();
while (!Serial.available());
c = Serial.read();
} else c=dispF.read();
color = palette[c-0x30];
return;
} else if (peek== 0x64) { // \d ファイル削除
Serial.println("File remove");
dispF.close();
SD.remove(input);Serial.read();
return;
} else if ((peek == 0x66) || (peek == 0x73)) { // \f ファイル読込 \s クリア
tft.fillScreen(BLUE);
x=0;y=0;yf=0;
tft.setScroll(tft.height());
if (peek==0x66) dispF = SD.open(input);
Serial.read();
return;
} else if ((peek >= 0x31) &
(peek <= 0x34)) { // \w 倍角
size = peek-0x30;
xsize = size; // 全角ピッチ
Serial.read();
return;
} else if ((peek >= 0x36) &
(peek <= 0x39)) { // \r Rotate
tft.setRotation(peek-0x36);
tft.setScroll(tft.height());
Serial.read();
return;
} else {
char othercode[20];
sprintf(othercode,"Another code=%2x",Serial.peek());
Serial.println(othercode);
}
}
// kanji = AsciiZen(kanji);
xsize = 8; // 半角ピッチ
// パターン取得
if (ROM) showSJIS1byte(kanji) ;
}
if (ROM==0){
unsigned long p = KanjiReadX(kanji, matrixdata32) ;
// 1バイトに満たない場合は穴埋めされるので
// それに合わせて穴埋めする。
ix = (p >> 24) & 0xff; ixb = (ix+7)>>3;
// 戻り値からフォントサイズのみ抜き出す。
iy = (p >> 16) & 0xff;
s = p & 0xffff;
// char st[16];
// sprintf(st, "%d,%d,size=%d\n", ix, iy, s);
// Serial.println(st);
// sendDotsToSerial32();
}
if (x > tft.width() - ix * size) { // Clip right
x = 0;
y = (y > tft.height()-(iy*size+2)*2)? 0:y+iy*size + 2;
if (yf || (y==0)) {
if (yf==0) {yf = 1;}
int rotate = tft.getRotation();
if (rotate==0) tft.scroll(tft.height()-y-(iy*size+2));
if (rotate==2) tft.scroll(y+(iy*size+2));
tft.fillRect(0, y, tft.width(), iy*size+2, bg);
}
}
// 表示用ループ。
if (ROM) { for (int i = 0; i < 8; i++) {
char byteDigit = (1 << i);
if (xsize<8) for (int b = 0; b < ix; b++) { // 全角をp/iy行分分散で描く
tft.fillRect(x + b*size, y+i*size, size, size, (matrixdata32[b] & byteDigit)? color:bg);
tft.fillRect(x + b*size, y+(8+i)*size, size, size, (matrixdata32[b+ix] & byteDigit)? color:bg);
}
else for (int b = 0; b < ix/2; b++) { // 半角をp/iy行分分散で描く
tft.fillRect(x + b*size, y+i*size, size, size, (matrixdata16[b] & byteDigit)? color:bg);
tft.fillRect(x + b*size, y+(8+i)*size, size, size, (matrixdata16[b+ix/2] & byteDigit)? color:bg);
}}
x += (xsize<8)? ix * size: ix/2*size;
}
else { // SD font
int z = 0,ys = 0;
// Serial.println(s);
// Serial.println(ixb);
while (z < s) {
for (int i = 0; i < 8; i++)
tft.fillRect(x + i*size, y+ys, size, size, (matrixdata32[z] & (1 << (7-i)))? color:bg);
x += 8*size;
if (!(++z % ixb)) {
ys += size;
x -= ixb*8*size;
}
}
x += ix * size;
}
}
/*シリアルモニタへ16*16のデータを表示する
void sendDotsToSerial32()
{
for (int i = 0; i < 8; i++) {
char byteDigit = (1 << i);
for (int b = 0; b < 16; b++)
Serial.write((matrixdata32[b] & byteDigit)? "XX":"--");
Serial.println();
}
for (int i = 0; i < 8; i++) {
char byteDigit = (1 << i);
for (int b = 16; b < 32; b++)
Serial.write((matrixdata32[b] & byteDigit)? "XX":"--");
Serial.println();
}
Serial.println();
} //sendDataToSerial32 */
RasPIのミニLCD漢字表示
TG12864Bという128x64ドット表示の グラフィックLCDが遊んでいたので、 RasPiにつないで、門真なむ様公開の 8x12のフォントを使い、自由に 漢字表示するプログラムを作りました。
参考にしたのは、ここですが、
次の4点を改良しました。
1)漢字コード系を自由に扱いたく、Python言語で書き替えました。
2)8×12の、割ときれいなフォントを扱うことができます。
3)GPIOピンの割り当てを自在にしました。
4)コマンドラインからも簡単に表示できます。
$ sudo python kanji812.py ☆グラフィック液晶に日本語表示☆8×12のビットマップフォントを使用して16文字を4行表示にしています。とても読み易い感触です。
<kanji812.py>
# -*- coding: utf-8 -*- import RPi.GPIO as GPIO import sys import time # コマンドの発行 def command(value, mode): GPIO.output(pinRS, mode) for i in range(len(pinDB)): GPIO.output(pinDB[i], (value \>\> i) \& 0x01) GPIO.output(pinE,True) GPIO.output(pinE,False) # ページの設定(縦アドレス0~7) def setPage(value): command(0xb8 | (value \& 0x07), False) # カラムの設定(横アドレス0~63) def setColumn(value): command(0x40 | (value \& 0x3f), False) # 8ビットのデータを書き込む # 書込んだ後、カラムアドレスは自動的に次へ移動する def writeData(value): command(value, True) # ディスプレイのICチップを選択 def selectIC(value): # 1=左側ディスプレイのIC1チップ 2=右側ディスプレイのIC2チップ if(value == 1): GPIO.output(pinCS1, True) GPIO.output(pinCS2, False) else: GPIO.output(pinCS1, False) GPIO.output(pinCS2, True) # 初期化 def init(): GPIO.setwarnings(False) GPIO.setmode(GPIO.BCM) time.sleep(0.05) GPIO.setup(pinRS, GPIO.OUT) GPIO.setup(pinE, GPIO.OUT) GPIO.setup(pinCS1, GPIO.OUT) GPIO.setup(pinCS2, GPIO.OUT) for i in pinDB: GPIO.setup(i, GPIO.OUT) GPIO.output(pinRS, False) GPIO.output(pinE, False) GPIO.output(pinCS1, False) GPIO.output(pinCS2, False) for i in pinDB: GPIO.output(i, False) for i in [1, 2]: selectIC(i) command(0xc0, False) # Display start line コマンド command(0x3f, False) # Display On コマンド # 画面クリア def cls(): for i in [1, 2]: selectIC(i) for j in range(9): setPage(j) setColumn(0) for k in range(65): writeData(0x00) yoko = int(1128/8-30) tate = 752 img = [[0 for x in range(yoko)] for y in range(tate)] # BMPデータを取り込む def readBMAP(): f = open("k8x12L_jisx0208.bmp", "rb") # ヘッダースキップ c = f.read(62) # 配列に読み込み global img for y in range(tate): c = f.read(30) # 未使用部分スキップ for x in range(yoko): img[y][x] = ord(f.read(1)) c = f.read(3) # 詰め物スキップ f.close() # 画面に描画 lcdLine = 0 def dispEUC(c1,txt): difku = (ord(txt[0:1]) -0xA1) \& 0xFF difb = difku+(difku\>\>1) difcd = ord(txt[1:2]) -0xA1 difcd *= 8 c = c1 - 1 selectIC(((c\&0x8)\>\>3)+1) setPage(lcdLine) setColumn(8*(c\&0x7)) for y in range(8): bb1 = img[tate-1-difcd-y][yoko-2-difb] bb2 = img[tate-1-difcd-y][yoko-1-difb] bb = ((bb1\<\<8) | bb2) \>\> 4 writeData(~(bb \& 0xFF) if (difku%2==1) else ~bb2) setPage(lcdLine+1) setColumn(8*(c\&0x7)) for y in range(8): bb1 = img[tate-1-difcd-y][yoko-2-difb] writeData(~(((bb1\>\>4) if (difku%2==1) else bb1) | 0xF0)) # 文字列の入力と変換 def inputUTF(): strg=raw_input(' 文字列を入力してください=\> ') reptEUC(strg) def reptEUC(txt): global lcdLine strg=txt.decode('utf-8').encode('euc-jp') skip=0 c=0 for i in range(len(strg)): if (skip==1): skip=0 continue if(((c%16)==0) \& (c\>0)): lcdLine+=2 code=ord(strg[i:i+1]) \& 0xFF if (code\<0x2F): if (code==0): break else: continue c+=1 if (code\<0x7F): if (code==0x5C): lcdLine+=2 c=0 skip=1 continue dispEUC(c,chr(0xA3)+chr(code|0x80)) continue dispEUC(c,strg[i:i+2]) skip=1 pinRS = 14 pinE = 15 pinCS1 = 17 pinCS2 = 18 pinDB = 8 * [0] pinDB[0] = 7 pinDB[1] = 8 pinDB[2] = 9 pinDB[3] = 10 pinDB[4] = 11 pinDB[5] = 22 pinDB[6] = 23 pinDB[7] = 24 param = sys.argv init() cls() readBMAP() if (len(param)\<2): inputUTF() else: reptEUC(param[1]) GPIO.cleanup()$ sudo python kanji812.py ☆グラフィック液晶に日本語表示☆8×12のビットマップフォントを使用して16文字を4行表示にしています。とても読み易い感触です。
カテゴリー: RaspberryPi, つれづれ
1件のコメント
5GHz対応Wifiドングル NETGEAR A6100
5GHz対応Wifiドングル NETGEAR A6100を
RaspberryPi2B/Jessie にインストールできたのでメモしておく。
<ツールの準備>
sudo apt-get install gcc make bc screen ncurses-dev
<Kernelの再構築作業>
Kernelソースの取得
$bash -c "$(curl -fsSSL https://raw.githubusercontent.com/moutend/raspi-kernel/master/raspi-kernel)"
#cd /usr/src/linux* (pwd:/usr/src/linux#)
#modprobe configs
#zcat /proc/config.gz > .config
#cp ../firmware/extra/Module7.symvers Module.symvers
Kernelのコンパイル
#make oldconfig
#make -j4 zImage modules dtbs
#make modules_install
/boot下を入替
#cp arch/arm/boot/dts/*.dtb /boot/
#cp arch/arm/boot/dts/overlays/*.dts /boot/overlays/
#cp arch/arm/boot/dts/overlays/README /boot/overlays/
#ls /boot | grep kernel
kernel.img kernel7.img
#cp /boot/kernel7.img /boot/kernel7.img.old
#scripts/mkknlimg arch/arm/boot/zImage /boot/kernel7.img
#reboot
<NETGEAR A6100のドライバー構築>
GitHubからドライバー・ソースの入手
$cd /usr/src
$sudo su
#git clone https://github.com/gnab/rtl8812au.git
#cd rtl8812au
Makefileを修正して、Pi用に変更
...
CONFIG_PLATFORM_I386_PC = n
...
CONFIG_PLATFORM_ARM_RPI = y
ドライバーのコンパイル
#make -j4
#make install
<Kernelバージョンに合わせ、ドライバーモジュールを設置>
#cp -p 8812au.ko /lib/modules/`uname -r`/kernel/drivers/net/wireless/
#/sbin/depmod `uname -r`
#insmod /lib/modules/'uname -r`/kernel/drivers/net/wireless/8812au.ko
#reboot
<ドライバーの動作を確認>
pi@raspberrypi:~ $ ip addr show wlan0
3: wlan0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000
link/ether a4:2b:8c:07:9d:33 brd ff:ff:ff:ff:ff:ff
inet 192.168.1.31/24 brd 192.168.1.255 scope global wlan0
valid_lft forever preferred_lft forever
inet6 2408:210:2484:5800:8a3e:7111:76b4:1dc2/64 scope global noprefixroute dynamic
valid_lft 14365sec preferred_lft 12565sec
inet6 fe80::7dae:9f4f:6d48:1d06/64 scope link
valid_lft forever preferred_lft forever
pi@raspberrypi:~ $ sudo iwlist wlan0 scan | grep GHz | sed 's/^ *//'
Frequency:5.22 GHz (Channel 44)
Frequency:2.412 GHz (Channel 1)
Frequency:2.412 GHz (Channel 1)
Frequency:2.442 GHz (Channel 7)
Frequency:2.447 GHz (Channel 8)
Frequency:2.462 GHz (Channel 11)
Frequency:5.5 GHz (Channel 100)
pi@raspberrypi:~ $
結果は、5GHzのAPもしっかりとSCANされている。
この後、DesktopのWirelessアイコンでAPを選択し、パスコードを入れる。
カテゴリー: RaspberryPi
コメントする
RaspBerryPiのマルチブート設定作業
複数のOSの選択起動ができるberrybootを使う時、既存のOSを追加する
ノウハウをメモしておく。
imgファイルをSquashFs形式に変換して、Addボタン長押しで指定する。
# installs kpartx and squashfs-tools sudo apt-get install kpartx squashfs-tools # # This opens your image file. #Change the DownloadedImage.img to what your image file name is. sudo kpartx -av DownloadedImage.img # # After opening the image it will give you at least two /dev/mapper/loop#p#. # You want the bigger of the partitions (Normally p2). # In this case it was loop 1 is the image and I want partition 2 because it is the bigger of the two. # sudo mount /dev/mapper/loop1p2 /mnt # Change # to the loop number the previous command reported. # sudo mount /dev/mapper/loop#p2 /mnt # # This is what make the image writable on berryboot # This line should work as is. It edits the file fstab on the image folder etc sudo sed -i 's/^\/dev\/mmcblk/#\0/g' /mnt/etc/fstab # # This line is what takes the mounted image and converts it the a squashfs image. # Note if you do this from the raspberry pi it will take several hours (dependent on the original image size). # Change NewBerryBoot.img to the desired image name. sudo mksquashfs /mnt NewBerryBoot.img -comp lzo -e lib/modules # # This unmounts the image you mounted at the beginning. # This line should work as is sudo umount /mnt # # This closes the image we opened at the beginning. # Change the DownloadedImage.img to what your image file name is. sudo kpartx -d DownloadedImage.img





