Program Listings

Master the Raspberry Pi Pico in C:

WiFi with lwIP & mbedtls

picomaster360

 

We have decided not to make the programs available as a download because this is not the point of the book - the programs are not finished production code but something you should type in and study.

The best solution is to provide the source code of the programs in a form that can be copied and pasted into a NetBeans or VS Code project. 

The only downside is that you have to create a project to paste the code into.

To do this follow the instructions in the book.

All of the programs below were copy and pasted from working programs in the IDE. They have been formatted using the built in formatter and hence are not identical in layout to the programs in the book. This is to make copy and pasting them easier. The programs in the book are formatted to be easy to read on the page.

Also notice that you will find complete listings of programs that are only slighly modified in the book and therefore not includes as a complete listing.The CMakeLists and other configuration files are also included here for completeness.

If anything you consider important is missing or if you have any requests or comments  contact:

This email address is being protected from spambots. You need JavaScript enabled to view it.


CHAPTER 1

Page 20 WiFi Simple Connect  Main program 

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

int setup(uint32_t country, const char *ssid, const char *pass,  uint32_t auth)
{
   if (cyw43_arch_init_with_country(country))
  {
    return 1;
  }
  cyw43_arch_enable_sta_mode();
  if (cyw43_arch_wifi_connect_blocking(ssid, pass, auth))
  {
    return 2;
  }
}

char ssid[] = "myhost";
char pass[] = "mypassword";
uint32_t country = CYW43_COUNTRY_mycountry;
uint32_t auth = CYW43_AUTH_WPA2_MIXED_PSK;

int main()
{
    stdio_init_all();
    setup(country, ssid, pass, auth);
    while (true)
    {
        sleep_ms(1);
    }
}

Page 21 WiFi Connect  CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()


add_executable(main
 main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})
target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background )
pico_add_extra_outputs(main)

Page 21 WiFi Connect lwiopts.h  - basic configuration file not listed in book

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H 

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#endif /* __LWIPOPTS_H__ */

 

 

Page 25 WiFi Connect setupWifi.h - used in most examples to connect to the AP.

int setup(uint32_t country, const char *ssid, const char *pass,
          uint32_t auth, const char *hostname, ip_addr_t *ip,
          ip_addr_t *mask, ip_addr_t *gw)
{

    if (cyw43_arch_init_with_country(country))
    {
        return 1;
    }

    cyw43_arch_enable_sta_mode();
    if (hostname != NULL)
    {
        netif_set_hostname(netif_default, hostname);
    }
    if (cyw43_arch_wifi_connect_async(ssid, pass, auth))
    {
        return 2;
    }
    int flashrate = 1000;
    int status = CYW43_LINK_UP + 1;
    while (status >= 0 && status != CYW43_LINK_UP)
    {
        int new_status = cyw43_tcpip_link_status(&cyw43_state,
                                                 CYW43_ITF_STA);
        if (new_status != status)
        {
            status = new_status;
            flashrate = flashrate / (status + 1);
            printf("connect status: %d %d\n", status, flashrate);
        }
        cyw43_arch_gpio_put(CYW43_WL_GPIO_LED_PIN, 1);
        sleep_ms(flashrate);
        cyw43_arch_gpio_put(CYW43_WL_GPIO_LED_PIN, 0);
        sleep_ms(flashrate);
    }
    if (status < 0)
    {
        cyw43_arch_gpio_put(CYW43_WL_GPIO_LED_PIN, 0);
    }
    else
    {
        cyw43_arch_gpio_put(CYW43_WL_GPIO_LED_PIN, 1);
        if (ip != NULL)
        {
            netif_set_ipaddr(netif_default, ip);
        }
        if (mask != NULL)
        {
            netif_set_netmask(netif_default, mask);
        }
        if (gw != NULL)
        {
            netif_set_gw(netif_default, gw);
        }

        printf("IP: %s\n",
               ip4addr_ntoa(netif_ip_addr4(netif_default)));
        printf("Mask: %s\n",
               ip4addr_ntoa(netif_ip_netmask4(netif_default)));
        printf("Gateway: %s\n",
               ip4addr_ntoa(netif_ip_gw4(netif_default)));
        printf("Host Name: %s\n",
               netif_get_hostname(netif_default));
    }
    return status;
}

int connect()
{
    char ssid[] = "ssid";
    char pass[] = "password";
    uint32_t country = CYW43_COUNTRY_code;
    uint32_t auth = CYW43_AUTH_WPA2_MIXED_PSK;
    return  setup(country, ssid, pass, auth, "MyPicoW", NULL, NULL, NULL);
}

Page 28 Scan main program  

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

static int scan_result(void *env, const cyw43_ev_scan_result_t *result)
{
    if (result)
    {
        printf("ssid: %-32s rssi: %4d chan: %3d mac: %02x:%02x:%02x:%02x:%02x:%02x sec: %u\n",
               result->ssid, result->rssi, result->channel,
               result->bssid[0], result->bssid[1], result->bssid[2], result->bssid[3], result->bssid[4], result->bssid[5],
               result->auth_mode);
    }
    return 0;
}

int main()
{
    stdio_init_all();

    if (cyw43_arch_init())
    {
        printf("failed to initialise\n");
        return 1;
    }

    cyw43_arch_enable_sta_mode();
    cyw43_wifi_set_up(&cyw43_state, CYW43_ITF_STA, true, CYW43_COUNTRY_UK);
    cyw43_wifi_scan_options_t scan_options = {0};
    int err = cyw43_wifi_scan(&cyw43_state, &scan_options, NULL, scan_result);

    while (true)
    {
        if (!cyw43_wifi_scan_active(&cyw43_state))
            break;
        sleep_ms(1000);
        printf("Scan in progress \n");
    }
    printf("Scan Complete\n");
    cyw43_arch_deinit();
    return 0;
}

Page 29 Get RSSI main program

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "setupWifi.h"

int main()
{
    stdio_init_all();
    connect();
    int32_t rssi;
    while (true)
    {
        sleep_ms(1000);
        cyw43_wifi_get_rssi(&cyw43_state, &rssi);
        printf("rssi: %d \n", rssi);
    }
}
 

Chapter 2

Page 38 Python HTTP Server

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO

class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):

    def sendResponse(self, cmd):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)
        self.send_response(200)
        self.end_headers()
        response = BytesIO()
        response.write(b'This is a '+bytes(cmd, 'utf-8')+
                                               b' request. ')
        response.write(b'Received: ')
        response.write(body)
        self.wfile.write(response.getvalue())

    def do_GET(self):
        self.send_response(200)
        self.end_headers()
        self.wfile.write(b'Hello, world!')


    def do_HEAD(self):
        self.send_response(200)
        self.end_headers()

    def do_POST(self):
        self.sendResponse("POST")

    def do_PUT(self):
        self.sendResponse("PUT")

    def do_DELETE(self):
        self.sendResponse("DELETE")

    def do_PATCH(self):
        self.sendResponse("PATCH")


httpd = HTTPServer(('', 8080), SimpleHTTPRequestHandler)
httpd.serve_forever()

Page 42  Simple HTTP Client using standard  lwipopts.h and cmakelists.txt 

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/tcp.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\nConnection: close\r\n\r\n";

err_t recv(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err)
{
 if (p != NULL)
 {
 printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
 pbuf_copy_partial(p, myBuff, p->tot_len, 0);
 myBuff[p->tot_len] = 0;
 printf("Buffer= %s\n", myBuff);
 tcp_recved(pcb, p->tot_len);
 pbuf_free(p);
 }
 return ERR_OK;
}

static err_t connected(void *arg, struct tcp_pcb *pcb, err_t err)
{
 err = tcp_write(pcb, header, strlen(header), 0);
 err = tcp_output(pcb);
 return ERR_OK;
}

int main()
{

 stdio_init_all();
 connect();

    struct tcp_pcb *pcb = tcp_new();
    tcp_recv(pcb, recv);
    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = tcp_connect(pcb, &ip, 80, connected);
    cyw43_arch_lwip_end();
    while (true)
    {
        sleep_ms(500);
    }
}

Page 44 Simple HTTP Client Using ALTCP

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\n\r\n";

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{

    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;
        printf("Buffer= %s\n", myBuff);
        altcp_recved(pcb, p->tot_len);
        pbuf_free(p);
    }
    return ERR_OK;
}

static err_t altcp_client_connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    err = altcp_write(pcb, header, strlen(header), 0);
    err = altcp_output(pcb);
    return ERR_OK;
}

int main()
{

    stdio_init_all();
    connect();

    struct altcp_pcb *pcb = altcp_new(NULL);
    altcp_recv(pcb, recv);

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(pcb, &ip, 80, altcp_client_connected);
    cyw43_arch_lwip_end();

    while (true)
    {
        sleep_ms(500);
    }
}
 

Add to the end of lwipopts.h

#define LWIP_ALTCP 1
 

 

Page 45 Not listed in full in book
Final Practical HTTP Client main.c - standard cmakelists.txt and lwipopts.h with  #define LWIP_ALTCP 1

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\n\r\n";

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{

    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
                if ((p->tot_len) > 2)
        {
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;        
        printf("Buffer= %s\n", myBuff);
        altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }    else
    {
        printf("Connection Closed");
        altcp_close(pcb);
    }
    return ERR_OK;
}

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

err_t altcp_client_connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    err = altcp_write(pcb, header, strlen(header), 0);
    err = altcp_output(pcb);

    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb){
        printf("Connection Closed");
        altcp_close(pcb);
}


int main()
{

    stdio_init_all();
    connect();

    struct altcp_pcb *pcb = altcp_new(NULL);
    altcp_recv(pcb, recv);
    altcp_sent(pcb, sent);
    altcp_err(pcb, err);
    altcp_poll(pcb, poll,10);

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(pcb, &ip, 80, altcp_client_connected);
    cyw43_arch_lwip_end();

    while (true)
    {
        sleep_ms(500);
    }
}

 


 

Chapter 3

Page 54 Not listed in full in book

Simple integer state request

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\n\r\n";

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{

    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        if ((p->tot_len) > 2)
        {
            pbuf_copy_partial(p, myBuff, p->tot_len, 0);
            myBuff[p->tot_len] = 0;
            *(int *)arg = 4;
            altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }
    else
    {
        printf("Connection Closed \n");
        altcp_close(pcb);
        *(int *)arg = 6;
    }
    return ERR_OK;
}

static err_t altcp_client_connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    *(int *)arg = 2;
    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb)
{
    printf("Connection Closed \n");
    *(int *)arg = 6;
    altcp_close(pcb);
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

int main()
{
    stdio_init_all();
    connect();

    int state = 0;
    struct altcp_pcb *pcb = altcp_new(NULL);

    altcp_recv(pcb, recv);
    altcp_sent(pcb, sent);
    altcp_err(pcb, err);
    altcp_poll(pcb, poll, 10);
    altcp_arg(pcb, &state);

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(pcb, &ip, 80, altcp_client_connected);
    cyw43_arch_lwip_end();
    state = 1;

    while (state != 0)
    {
        switch (state)
        {
        case 0:
        case 1:
        case 3:
            break;

        case 2:
            state = 3;
            cyw43_arch_lwip_begin();
            err = altcp_write(pcb, header, strlen(header), 0);
            err = altcp_output(pcb);
            cyw43_arch_lwip_end();
            break;
        case 4:
            state = 5;
            break;
        case 6:
            printf("Buffer= %s\n", myBuff);
            state = 0;
            break;
        default:
            sleep_ms(1000);
            printf("LED Flash\n");
        }
    }
    printf("Data Transfered\n");
}

Page 59 State use a struct

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\n\r\n";

struct connectionState
{
    int state;
    struct altcp_pcb *pcb;
    char *myBuff;
    int start;
};

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        if ((p->tot_len) > 2)
        {
            pbuf_copy_partial(p, (cs->myBuff) + (cs->start), p->tot_len, 0);
            cs->start += p->tot_len;
            cs->myBuff[cs->start] = 0;
            cs->state = 4;
            altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }
    else
    {
        printf("Connection Closed\n");
        altcp_close(pcb);
        cs->state = 6;
    }
    return ERR_OK;
}

static err_t connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 2;
    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb)
{
    printf("Connection Closed \n");
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 6;
    altcp_close(pcb);
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

err_t newConnection(struct connectionState *cs, char *buf)
{
    cs->state = 0;
    cs->pcb = altcp_new(NULL);
    altcp_recv(cs->pcb, recv);
    altcp_sent(cs->pcb, sent);
    altcp_err(cs->pcb, err);
    altcp_poll(cs->pcb, poll, 10);
    altcp_arg(cs->pcb, cs);
    cs->myBuff = buf;
    cs->start = 0;
    return ERR_OK;
}

int pollConnection(struct connectionState *cs)
{

    switch (cs->state)
    {
    case 0:
    case 1:
    case 3:
    case 6:
        break;
    case 2:
        cs->state = 3;
        cyw43_arch_lwip_begin();
        err_t err = altcp_write(cs->pcb, header, strlen(header), 0);
        err = altcp_output(cs->pcb);
        cyw43_arch_lwip_end();
        break;
    case 4:
        cs->state = 5;
        break;
    }
    return cs->state;
}

int main()
{
    stdio_init_all();
    connect();

    struct connectionState cs;
    newConnection(&cs, myBuff);

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs.pcb, &ip, 80, connected);
    cyw43_arch_lwip_end();
    cs.state = 1;
    while (true)
    {
        if (pollConnection(&cs) == 6)
        {
            printf("Buffer= %s\n", cs.myBuff);
            cs.state = 0;
            break;
        }
        sleep_ms(1000);
        printf("LED Flash\n");
    }
    printf("Data Transfered\n");
}

 

Page 65 Non blocking general Request.h

struct connectionState
{
    int state;
    struct altcp_pcb *pcb;
    char *sendData;
    char *recvData;
    int start;
};

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        if ((p->tot_len) > 2)
        {
            pbuf_copy_partial(p, (cs->recvData) + (cs->start), p->tot_len, 0);
            cs->start += p->tot_len;
            cs->recvData[cs->start] = 0;
            cs->state = 4;
            altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }
    else
    {            
        cs->state = 6;
    }
    return ERR_OK;
}

static err_t connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 2;
    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb)
{
    printf("Connection Closed \n");
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 6;
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

struct connectionState *newConnection(char *sendData, char *recvData)
{
    struct connectionState *cs = (struct connectionState *)malloc(sizeof(struct connectionState));
    cs->state = 0;
    cs->pcb = altcp_new(NULL);
    altcp_recv(cs->pcb, recv);
    altcp_sent(cs->pcb, sent);
    altcp_err(cs->pcb, err);
    altcp_poll(cs->pcb, poll, 10);
    altcp_arg(cs->pcb, cs);
    cs->sendData = sendData;
    cs->recvData = recvData;
    cs->start = 0;
    return cs;
}

struct connectionState *doRequest(ip_addr_t *ip, char *host, u16_t port, char *request, char *file, char *sendData, char *recvData)
{
    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n%s";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    char *requestData = malloc(len + 1);
    snprintf(requestData, len + 1, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    struct connectionState *cs = newConnection(requestData, recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}

int pollRequest(struct connectionState **pcs)
{
    if(*pcs==NULL) return 0;
    struct connectionState *cs=*pcs;
    switch (cs->state)
    {
    case 0:
    case 1:
    case 3:
        break;

    case 2:
        cs->state = 3;
        cyw43_arch_lwip_begin();
        err_t err = altcp_write(cs->pcb, cs->sendData, strlen(cs->sendData), 0);
        err = altcp_output(cs->pcb);
        cyw43_arch_lwip_end();
        break;
    case 4:
        cs->state = 5;
        break;
    case 6:
        cyw43_arch_lwip_begin();
        altcp_close(cs->pcb);
        cyw43_arch_lwip_end();
        free(cs);
        *pcs = NULL;
        return 0;
    }
    return cs->state;
}
 

Page 27 Non blocking Request main program downloading two requests.

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "lwip/altcp.h"
#include "setupWifi.h"
#include "request.h"
#define BUF_SIZE 2048
char myBuff1[BUF_SIZE];
char myBuff2[BUF_SIZE];

int main()
{
    stdio_init_all();
    connect();

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    struct connectionState *cs1 = doRequest(&ip, "example.com", 80, "GET", "/", NULL, myBuff1);
    IP4_ADDR(&ip, 192, 168, 11, 101);
    struct connectionState *cs2 = doRequest(&ip, "192.168.11.101", 8080, "PUT", "/", "Hello PUT world", myBuff2);

    while (pollRequest(&cs1) + pollRequest(&cs2))
    {
        sleep_ms(100);
    }
    printf("Both complete\n");
    printf("Buffer 1 = \n%s\n\n", myBuff1);
    printf("Buffer 2 = \n%s\n\n", myBuff2);

    printf("Data Transferred\n");
    cyw43_arch_deinit();
    return 0;
}
 
 

Page 70 Temperature PUT client main program

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#include "request.h"

#define BUF_SIZE 4096
char myBuff1[BUF_SIZE];

int readTemp()
{
    return 33;
}

int main()
{
    char ssid[] = "laribina";
    char pass[] = "hawkhawk";
    uint32_t country = CYW43_COUNTRY_UK;
    uint32_t auth = CYW43_AUTH_WPA2_MIXED_PSK;
    stdio_init_all();
    setup(country, ssid, pass, auth, "MyPicoW", NULL, NULL, NULL);

    ip_addr_t ip;
    IP4_ADDR(&ip, 192, 168, 11, 101);

    while (true)
    {
        int t = readTemp();
        int len = snprintf(NULL, 0, "%d", t);
        char *requestData = malloc(len + 1);
        snprintf(requestData, len + 1, "%d", t);
        printf("%s\n",requestData);
        struct connectionState *cs1 = doRequest(&ip, "192.168.11.101", 8080, "PUT", "/", requestData, myBuff1);
        while (pollRequest(&cs1) )
        {
            sleep_ms(200);
        }
        printf("%s\n",myBuff1);
        sleep_ms(5000);
    }
    return 0;
}
 
 
 

Page 71 Custom Sever For the PUT Temperature Client

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO

class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):
    def log_message(self,*args, **kwargs):
        pass

    def do_PUT(self):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)
        bodyString= body.decode(encoding="utf-8")
        temp=float(bodyString)
        print(temp,"C")
        self.send_response(200)
        self.end_headers()

httpd = HTTPServer(('', 8080), SimpleHTTPRequestHandler)
httpd.serve_forever()

Page 72 full listing not in book

Binary request version of request.h

struct connectionState
{
    int state;
    struct altcp_pcb *pcb;
    char *sendData;
    int bytes;
    char *recvData;
    int start;
};

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        if ((p->tot_len) > 2)
        {
            pbuf_copy_partial(p, (cs->recvData) + (cs->start), p->tot_len, 0);
            cs->start += p->tot_len;
            cs->recvData[cs->start] = 0;
            cs->state = 4;
            altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }
    else
    {
        cs->state = 6;
    }
    return ERR_OK;
}

static err_t connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 2;
    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb)
{
    printf("Connection Closed \n");
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 6;
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

struct connectionState *newConnection(char *sendData, int bytes, char *recvData)
{
    struct connectionState *cs = (struct connectionState *)malloc(sizeof(struct connectionState));
    cs->state = 0;
    cs->pcb = altcp_new(NULL);
    altcp_recv(cs->pcb, recv);
    altcp_sent(cs->pcb, sent);
    altcp_err(cs->pcb, err);
    altcp_poll(cs->pcb, poll, 10);
    altcp_arg(cs->pcb, cs);
    cs->sendData = sendData;
    cs->bytes=bytes;
    cs->recvData = recvData;
    cs->start = 0;
    return cs;
}

struct connectionState *doRequest(ip_addr_t *ip, char *host, u16_t port, char *request, char *file, char *sendData, char *recvData)
{
    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n%s";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    char *requestData = malloc(len + 1);
    snprintf(requestData, len + 1, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    struct connectionState *cs = newConnection(requestData, strlen(requestData),recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}

struct connectionState *doRequestBinary(ip_addr_t *ip, char *host, u16_t port, char *request, char *file, char *sendData, int bytes, char *recvData)
{

    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, bytes);
    char *requestData = malloc(len + bytes + 1);
    snprintf(requestData, len + 1, headerTemplate, request, file, host, port, bytes);
    memcpy(requestData + len, sendData, bytes);
    struct connectionState *cs = newConnection(requestData, len + bytes, recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}

int pollRequest(struct connectionState **pcs)
{
    if (*pcs == NULL)
        return 0;
    struct connectionState *cs = *pcs;
    switch (cs->state)
    {
    case 0:
    case 1:
    case 3:
        break;

    case 2:
        cs->state = 3;
        cyw43_arch_lwip_begin();
        err_t err = altcp_write(cs->pcb, cs->sendData, cs->bytes, 0);
        err = altcp_output(cs->pcb);
        cyw43_arch_lwip_end();
        break;
    case 4:
        cs->state = 5;
        break;
    case 6:
        cyw43_arch_lwip_begin();
        altcp_close(cs->pcb);
        cyw43_arch_lwip_end();
        free(cs);
        *pcs = NULL;
        return 0;
    }
    return cs->state;
}

Page 74 Binary request main program

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "lwip/altcp.h"

#include "request.h"

#define BUF_SIZE 4096
char myBuff1[BUF_SIZE];

int main()
{
    char ssid[] = "laribina";
    char pass[] = "hawkhawk";
    uint32_t country = CYW43_COUNTRY_UK;
    uint32_t auth = CYW43_AUTH_WPA2_MIXED_PSK;
    stdio_init_all();
    setup(country, ssid, pass, auth, "MyPicoW", NULL, NULL, NULL);

    char randdata[500];
    ip_addr_t ip;
    IP4_ADDR(&ip, 192, 168, 11, 101);
    for (int p = 0; p < 500; p++)
    {
        randdata[p] = (uint8_t)rand();
    }
    struct connectionState *cs1 = doRequestBinary(&ip, "192.168.11.101", 8080, "PUT", "/", randdata, 500, myBuff1);
    while (pollRequest(&cs1))
    {
        sleep_ms(200);
    }
    printf("%s\n", myBuff1);

    return 0;
}

Page 75 Python Custom server for Binary request

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO

class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):
    def log_message(self,*args, **kwargs):
        pass

    def do_PUT(self):  
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)
        print(content_length)      
        with open("data.bin",mode="wb") as f:
            f.write(body)  
        self.send_response(200)
        self.end_headers()
        response = BytesIO()
        response.write(b'Received:' )      
        self.wfile.write(response.getvalue())

httpd = HTTPServer(('', 8080), SimpleHTTPRequestHandler)
httpd.serve_forever()

Page 77 full listing not in book

DNS Main Program needs requests.h 

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "lwip/altcp.h"
#include "lwip/dns.h"
#include "setupWifi.h"
#include "request.h"
#define BUF_SIZE 2048
char myBuff1[BUF_SIZE];

void dns_found(const char *name, const ip_addr_t *ip, void *arg)
{
    ip_addr_t *ipResult = (ip_addr_t *)arg;
    if (ip)
    {
        ip4_addr_copy(*ipResult, *ip);
    }
    else
    {
        ip4_addr_set_loopback(ipResult);
    }
    return;
}

err_t getIP(char *URL, ip_addr_t *ipResult)
{
    cyw43_arch_lwip_begin();
    err_t err = dns_gethostbyname(URL, ipResult, dns_found, ipResult);
    cyw43_arch_lwip_end();
    return err;
}

int main()
{
    stdio_init_all();
    connect();

    ip_addr_t ip;
    ip4_addr_set_zero(&ip);
    getIP("example.com", &ip);
    while (!ip_addr_get_ip4_u32(&ip))
    {
        sleep_ms(100);
    };
    if (ip4_addr_isloopback(&ip))
    {
        printf("address not found");
    }
    struct connectionState *cs1 = doRequest(&ip, "example.com", 80, "GET", "/", NULL, myBuff1);

    while (pollRequest(&cs1))
    {
        sleep_ms(100);
    }
    printf("Buffer 1 = \n%s\n\n", myBuff1);

    printf("Data Transferred\n");
    cyw43_arch_deinit();
    return 0;
}


Chapter 4

Page 90  Simple TLS Client  main.c

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "lwip/altcp.h"
#include "lwip/altcp_tls.h"

#include "setupWifi.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];
char header[] = "GET /index.html HTTP/1.1\r\nHOST:example.com\r\n\r\n";

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{

    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;
        printf("Buffer= %s\n", myBuff);
        altcp_recved(pcb, p->tot_len);
        pbuf_free(p);
    }
    return ERR_OK;
}

static err_t altcp_client_connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    err = altcp_write(pcb, header, strlen(header), 0);
    err = altcp_output(pcb);

    return ERR_OK;
}

int main()
{

    stdio_init_all();
    connect();

    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);
    struct altcp_pcb *pcb = altcp_tls_new(tls_config, IPADDR_TYPE_ANY);
    mbedtls_ssl_set_hostname(altcp_tls_context(pcb), "example.com");
    altcp_recv(pcb, recv);



    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(pcb, &ip, 443, altcp_client_connected);
    cyw43_arch_lwip_end();
    while (true)
    {
        sleep_ms(500);
    }
}

Page 90 Simple TLS Client cmakelists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()


add_executable(main
 main.c
)


target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_mbedtls
pico_mbedtls)
pico_add_extra_outputs(main)

Page 88 Simple TLS Client mbedtls_config.h

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
 #define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C
//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client and server modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 90 full listing not in book

Simple TLS Client lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define LWIP_ALTCP               1
#define LWIP_ALTCP_TLS           1
#define LWIP_ALTCP_TLS_MBEDTLS   1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG  LWIP_DBG_ON

#endif /* __LWIPOPTS_H__ */

Page 92 Full listing not in book

TLS Request.h

struct connectionState
{
    int state;
    struct altcp_pcb *pcb;
    char *sendData;
    int bytes;
    char *recvData;
    int start;
};

err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    printf("data sent %d\n", len);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        if ((p->tot_len) > 2)
        {
            pbuf_copy_partial(p, (cs->recvData) + (cs->start), p->tot_len, 0);
            cs->start += p->tot_len;
            cs->recvData[cs->start] = 0;
            cs->state = 4;
            altcp_recved(pcb, p->tot_len);
        }
        pbuf_free(p);
    }
    else
    {
        cs->state = 6;
    }
    return ERR_OK;
}

static err_t connected(void *arg, struct altcp_pcb *pcb, err_t err)
{
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 2;
    return ERR_OK;
}

err_t poll(void *arg, struct altcp_pcb *pcb)
{
    printf("Connection Closed \n");
    struct connectionState *cs = (struct connectionState *)arg;
    cs->state = 6;
}

void err(void *arg, err_t err)
{
    if (err != ERR_ABRT)
    {
        printf("client_err %d\n", err);
    }
}

struct connectionState *newConnection(char *sendData, int bytes, char *recvData)
{
    struct connectionState *cs = (struct connectionState *)malloc(sizeof(struct connectionState));
    cs->state = 0;
    cs->pcb = altcp_new(NULL);
    altcp_recv(cs->pcb, recv);
    altcp_sent(cs->pcb, sent);
    altcp_err(cs->pcb, err);
    altcp_poll(cs->pcb, poll, 10);
    altcp_arg(cs->pcb, cs);
    cs->sendData = sendData;
    cs->bytes=bytes;
    cs->recvData = recvData;
    cs->start = 0;
    return cs;
}

struct connectionState *newTLSConnection(char* host, char *sendData, int bytes, char *recvData)
{
    struct connectionState *cs = (struct connectionState *)malloc(sizeof(struct connectionState));
    cs->state = 0;

    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);
    cs->pcb = altcp_tls_new(tls_config, IPADDR_TYPE_ANY);    
    mbedtls_ssl_set_hostname(altcp_tls_context(cs->pcb), host);
    altcp_recv(cs->pcb, recv);
    altcp_sent(cs->pcb, sent);
    altcp_err(cs->pcb, err);
    altcp_poll(cs->pcb, poll, 10);
    altcp_arg(cs->pcb, cs);
    cs->sendData = sendData;
    cs->bytes=bytes;
    cs->recvData = recvData;
    cs->start = 0;
    return cs;
}

struct connectionState *doRequest(ip_addr_t *ip, char *host, u16_t port, char *request, char *file, char *sendData, char *recvData)
{
    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n%s";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    char *requestData = malloc(len + 1);
    snprintf(requestData, len + 1, headerTemplate, request, file, host, port, strlen(sendData), sendData);
    struct connectionState *cs = newConnection(requestData, strlen(requestData),recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}

struct connectionState *doRequestBinary(ip_addr_t *ip, char *host, u16_t port, char *request, char *file, char *sendData, int bytes, char *recvData)
{

    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, bytes);
    char *requestData = malloc(len + bytes + 1);
    snprintf(requestData, len + 1, headerTemplate, request, file, host, port, bytes);
    memcpy(requestData + len, sendData, bytes);
    struct connectionState *cs = newConnection(requestData, len + bytes, recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}


struct connectionState *doTLSRequestBinary(ip_addr_t *ip, char *host, u16_t port, char *request, char *file,  char *sendData,int bytes, char *recvData)
{

    char headerTemplate[] = "%s %s HTTP/1.1\r\nHOST:%s:%d\r\nConnection: close\r\nContent-length: %d\r\n\r\n";
    int len = snprintf(NULL, 0, headerTemplate, request, file, host, port, bytes);
    char *requestData = malloc(len + bytes+1);
    snprintf(requestData, len+1, headerTemplate, request, file, host, port, bytes);
    memcpy(requestData+len,sendData,bytes);  
    struct connectionState *cs = newTLSConnection(host,requestData,len+bytes ,recvData);
    cyw43_arch_lwip_begin();
    err_t err = altcp_connect(cs->pcb, ip, port, connected);
    cyw43_arch_lwip_end();
    cs->state = 1;
    return cs;
}


int pollRequest(struct connectionState **pcs)
{
    if (*pcs == NULL)
        return 0;
    struct connectionState *cs = *pcs;
    switch (cs->state)
    {
    case 0:
    case 1:
    case 3:
        break;

    case 2:
        cs->state = 3;
        cyw43_arch_lwip_begin();
        err_t err = altcp_write(cs->pcb, cs->sendData, cs->bytes, 0);
        err = altcp_output(cs->pcb);
        cyw43_arch_lwip_end();
        break;
    case 4:
        cs->state = 5;
        break;
    case 6:
        cyw43_arch_lwip_begin();
        altcp_close(cs->pcb);
        cyw43_arch_lwip_end();
        free(cs);
        *pcs = NULL;
        return 0;
    }
    return cs->state;
}

Page 94 RequestTLS Client Main.c

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/altcp_tcp.h"
#include "lwip/altcp_tls.h"
#include "setupWifi.h"

#include "request.h"

#define BUF_SIZE 2048
char myBuff[BUF_SIZE];

int main()
{

    stdio_init_all();
    connect();

    ip_addr_t ip;
    IP4_ADDR(&ip, 93, 184, 216, 34);

    struct connectionState *cs1 = doTLSRequestBinary(&ip, "example.com", 443, "GET", "/", NULL, 0, myBuff);
    while (pollRequest(&cs1))
    {
        sleep_ms(200);
    }
    printf("%s\n", myBuff);

    return 0;
}

Chapter 5

Page 105 RandomByte function

uint8_t randomByte()
{
    uint32_t random = 0;
    uint32_t bit = 0;
    for (int k = 0; k < 8; k++)
    {
        while (true)
        {
            bit = rosc_hw->randombit;
            sleep_us(10);
            if (bit != rosc_hw->randombit)
                break;
        }

        random = (random << 1) | bit;
    }

    return (uint8_t)random;
}

Page 111 Full listing not in book

Adding EC and GCM to mbedtls_config.h in Client and server mode

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C



//EC KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_ECDHE_RSA_ENABLED
#define MBEDTLS_ECDH_C
#define MBEDTLS_ECDSA_C
#define MBEDTLS_ECP_C

/* Short Weierstrass curves (supporting ECP, ECDH, ECDSA) */
#define MBEDTLS_ECP_DP_SECP192R1_ENABLED
#define MBEDTLS_ECP_DP_SECP224R1_ENABLED
#define MBEDTLS_ECP_DP_SECP256R1_ENABLED
#define MBEDTLS_ECP_DP_SECP384R1_ENABLED
#define MBEDTLS_ECP_DP_SECP521R1_ENABLED
#define MBEDTLS_ECP_DP_SECP192K1_ENABLED
#define MBEDTLS_ECP_DP_SECP224K1_ENABLED
#define MBEDTLS_ECP_DP_SECP256K1_ENABLED
#define MBEDTLS_ECP_DP_BP256R1_ENABLED
#define MBEDTLS_ECP_DP_BP384R1_ENABLED
#define MBEDTLS_ECP_DP_BP512R1_ENABLED

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C

//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES
#define MBEDTLS_GCM_C

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client and server modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION

#define MBEDTLS_SSL_SRV_C

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 115 AES ECB Mode Main Program

#include <stdio.h>
#include "pico/stdlib.h"
#include "mbedtls/cipher.h"

#include "pico/rand.h"

int main()
{
    stdio_init_all();
    int ret;


    mbedtls_cipher_context_t cipher_ctx;
    mbedtls_cipher_init(&cipher_ctx);

    const mbedtls_cipher_info_t *cipher_info;
    cipher_info = mbedtls_cipher_info_from_string("AES-128-ECB");
    ret = mbedtls_cipher_setup(&cipher_ctx, cipher_info);

    unsigned char key[16];
    get_rand_128((rng_128_t*)key );


    ret = mbedtls_cipher_setkey(&cipher_ctx, key, cipher_info->key_bitlen, MBEDTLS_ENCRYPT);
    ret = mbedtls_cipher_reset(&cipher_ctx);

    char buffer[16] = "Hello World";
    char output[16];
    int olen;
    ret = mbedtls_cipher_update(&cipher_ctx, buffer, 16, output, &olen);
    printf("cipher text ");
    for (int i = 0; i < olen; i++)
    {
        printf("%02X", output[i]);
    }
    printf("\n");

    char plaintext[16];  
    ret = mbedtls_cipher_setkey(&cipher_ctx, key, cipher_info->key_bitlen, MBEDTLS_DECRYPT);
    ret = mbedtls_cipher_reset(&cipher_ctx);
    mbedtls_cipher_update(&cipher_ctx, output, 16, plaintext, &olen);
    printf("plain text %.16s\n", plaintext);
    return 0;
}

Page 116 AES ECB mbedtls_config.h

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES

#define MBEDTLS_CIPHER_C

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 116 AES ECB Mode CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

 add_executable(main

   main.c
)
target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_mbedtls)
pico_add_extra_outputs(main)

Page 118 Full listing not in book

AES CBC Mode Main Program including list of available encryptions.

#include <stdio.h>
#include "pico/stdlib.h"
#include "mbedtls/cipher.h"

#include "pico/rand.h"

int main()
{
    stdio_init_all();
    int ret;

    const mbedtls_cipher_info_t *cipher_info1;
    const int *list;
    printf("Available ciphers:\n");
    list = mbedtls_cipher_list();
    while (*list)
    {
        cipher_info1 = mbedtls_cipher_info_from_type(*list);
        printf("  %s\n", cipher_info1->name);
        list++;
    }

    mbedtls_cipher_context_t cipher_ctx;
    mbedtls_cipher_init(&cipher_ctx);

    const mbedtls_cipher_info_t *cipher_info;
    cipher_info = mbedtls_cipher_info_from_string("AES-128-CBC");
    ret = mbedtls_cipher_setup(&cipher_ctx, cipher_info);

    unsigned char key[16];
    get_rand_128((rng_128_t *)key);
    ret = mbedtls_cipher_setkey(&cipher_ctx, key, cipher_info->key_bitlen, MBEDTLS_ENCRYPT);

    unsigned char IV[16];
    get_rand_128((rng_128_t *)IV);
    ret = mbedtls_cipher_set_iv(&cipher_ctx, IV, 16);

    ret = mbedtls_cipher_reset(&cipher_ctx);

    char buffer[16] = "Hello World";
    char output[16];
    int olen;
    ret = mbedtls_cipher_update(&cipher_ctx, buffer, 16, output, &olen);

    printf("cipher text ");
    for (int i = 0; i < olen; i++)
    {
        printf("%02X", output[i]);
    }
    printf("\n");

    char plaintext[16];
    ret = mbedtls_cipher_setkey(&cipher_ctx, key, cipher_info->key_bitlen, MBEDTLS_DECRYPT);   
    ret = mbedtls_cipher_set_iv(&cipher_ctx, IV, 16);
    ret = mbedtls_cipher_reset(&cipher_ctx);
    ret = mbedtls_cipher_update(&cipher_ctx, output, 16, plaintext, &olen);
    printf("plain text %.16s\n", plaintext);
    return 0;
}

Chapter 6

Page 130 Simple HTTP Server Main Program 

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/altcp_tcp.h"

#include "hardware/rtc.h"
#include "time.h"

#include "setupWifi.h"

#define BUF_SIZE 2048

void getDateNow(struct tm *t)
{
    datetime_t rtc;
    rtc_get_datetime(&rtc);

    t->tm_sec = rtc.sec;
    t->tm_min = rtc.min;
    t->tm_hour = rtc.hour;
    t->tm_mday = rtc.day;
    t->tm_mon = rtc.month - 1;
    t->tm_year = rtc.year - 1900;
    t->tm_wday = rtc.dotw;
    t->tm_yday = 0;
    t->tm_isdst = -1;
}

void sendData(struct altcp_pcb *pcb)
{
    err_t err;
    char html[] = "<html><head><title>Temperature</title></head><body><p>{\"humidity\":81%, \"airtemperature\":23.5C}</p></body></html>\r\n";
    char headers[1024] = {0};
    char Status[] = "HTTP/1.1 200 OK\r\nContent-Type: text/html;charset=UTF-8\r\nServer:Picow\r\n";

    struct tm t;
    getDateNow(&t);
    char Date[100];
    strftime(Date, sizeof(Date), "Date: %a, %d %b %Y %k:%M:%S %Z\r\n", &t);

    char ContLen[100] = {0};
    snprintf(ContLen, sizeof ContLen, "Content-Length:%d \r\n", strlen(html));
    snprintf(headers, sizeof headers, "%s%s%s\r\n", Status, Date, ContLen);

    char data[2048] = {0};
    snprintf(data, sizeof data, "%s%s", headers, html);

    err = altcp_write(pcb, data, strlen(data), 0);
    err = altcp_output(pcb);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    char myBuff[BUF_SIZE];
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;
        printf("Buffer= %s\n", myBuff);
        altcp_recved(pcb, p->tot_len);
        pbuf_free(p);
        sendData(pcb);
    }
    return ERR_OK;
}

static err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    altcp_close(pcb);
}

static err_t accept(void *arg, struct altcp_pcb *pcb, err_t err)
{
    altcp_recv(pcb, recv);
    altcp_sent(pcb, sent);
    printf("connect!\n");

    return ERR_OK;
}

void setRTC()
{
    datetime_t t = {
        .year = 2023,
        .month = 02,
        .day = 03,
        .dotw = 5,
        .hour = 11,
        .min = 10,
        .sec = 00};
    rtc_init();
    rtc_set_datetime(&t);
}

int main()
{
    stdio_init_all();
    setRTC();
    connect();
    struct altcp_pcb *pcb = altcp_new(NULL);
    altcp_accept(pcb, accept);

    altcp_bind(pcb, IP_ADDR_ANY, 80);
    cyw43_arch_lwip_begin();
    pcb = altcp_listen_with_backlog(pcb, 3);
    cyw43_arch_lwip_end();
    while (true)
    {
        sleep_ms(500);
    }
}

Page 133 Full listing not in book

Simple HTTP Server lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define LWIP_ALTCP               1

#define LWIP_DEBUG 1
#define TCP_LISTEN_BACKLOG       1
#endif /* __LWIPOPTS_H__ */

Page 113 Full listing not in book

Simple HTTP Server CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
 main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background hardware_rtc)
pico_add_extra_outputs(main)

Page 136 Python program to convert certificate to C code

import binascii

with open("iopress.key", 'rb') as f:
    lines = f.readlines()
lines = b"".join(lines[1:-1])
key = binascii.a2b_base64(lines)

res = ""

for b in key:
    res += "0x%02x," % b

res="u8_t key[]={"+res[:-1]+"};"
print(res)

with open("iopress.crt", 'rb') as f:
    lines = f.readlines()
lines = b"".join(lines[1:-1])
cert = binascii.a2b_base64(lines)
res = ""
for b in cert:
    res += "0x%02x," % b

res="u8_t cert[]={"+res[:-1]+"};"
print()
print(res)

Page 137 Full listing not in book

Simple HTTPS Server Main Program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/altcp_tcp.h"

#include "lwip/altcp_tls.h"
#include "hardware/structs/rosc.h"

#include "hardware/rtc.h"
#include "time.h"

#include "setupWifi.h"

#define BUF_SIZE 2048

void getDateNow(struct tm *t)
{
    datetime_t rtc;
    rtc_get_datetime(&rtc);

    t->tm_sec = rtc.sec;
    t->tm_min = rtc.min;
    t->tm_hour = rtc.hour;
    t->tm_mday = rtc.day;
    t->tm_mon = rtc.month - 1;
    t->tm_year = rtc.year - 1900;
    t->tm_wday = rtc.dotw;
    t->tm_yday = 0;
    t->tm_isdst = -1;
}

void sendData(struct altcp_pcb *pcb)
{
    err_t err;
    char html[] = "<html><head><title>Temperature</title></head><body><p>{\"humidity\":81%, \"airtemperature\":23.5C}</p></body></html>\r\n";
    char headers[1024] = {0};
    char Status[] = "HTTP/1.1 200 OK\r\nContent-Type: text/html;charset=UTF-8\r\nServer:Picow\r\n";

    struct tm t;
    getDateNow(&t);
    char Date[100];
    strftime(Date, sizeof(Date), "Date: %a, %d %b %Y %k:%M:%S %Z\r\n", &t);

    char ContLen[100] = {0};
    snprintf(ContLen, sizeof ContLen, "Content-Length:%d \r\n", strlen(html));
    snprintf(headers, sizeof headers, "%s%s%s\r\n", Status, Date, ContLen);

    char data[2048] = {0};
    snprintf(data, sizeof data, "%s%s", headers, html);

    err = altcp_write(pcb, data, strlen(data), 0);
    err = altcp_output(pcb);
}

err_t recv(void *arg, struct altcp_pcb *pcb, struct pbuf *p, err_t err)
{
    char myBuff[BUF_SIZE];
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d err %d\n", p->tot_len, p->len, p->next, err);
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;
        printf("Buffer= %s\n", myBuff);
        altcp_recved(pcb, p->tot_len);
        pbuf_free(p);
        sendData(pcb);
    }
    return ERR_OK;
}

static err_t sent(void *arg, struct altcp_pcb *pcb, u16_t len)
{
    altcp_close(pcb);
}

static err_t accept(void *arg, struct altcp_pcb *pcb, err_t err)
{
    altcp_recv(pcb, recv);
    altcp_sent(pcb, sent);
    printf("connect!\n");

    return ERR_OK;
}

void setRTC()
{
    datetime_t t = {
        .year = 2023,
        .month = 02,
        .day = 03,
        .dotw = 5,
        .hour = 11,
        .min = 10,
        .sec = 00};
    rtc_init();
    rtc_set_datetime(&t);
}

int main()
{
    stdio_init_all();
    setRTC();

    connect();

    u8_t key[] = {0x30, 0x82, 0x04, 0xbd, 0x02, 0x01, 0x00, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x04, 0x82, 0x04, 0xa7, 0x30, 0x82, 0x04, 0xa3, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbd, 0xb3, 0xb6, 0x94, 0x9f, 0x87, 0x85, 0xd6, 0xd4, 0xd0, 0xf9, 0x24, 0x4b, 0x8c, 0x7d, 0x9e, 0xf5, 0x83, 0xac, 0x90, 0x37, 0x5b, 0xdf, 0x4d, 0x9b, 0x05, 0x6b, 0x5f, 0xaa, 0x87, 0x31, 0x87, 0x0e, 0x97, 0x90, 0xa0, 0xff, 0x12, 0x81, 0xcc, 0xfe, 0x66, 0xa3, 0x8e, 0x34, 0x33, 0x63, 0x27, 0x10, 0xa4, 0xf1, 0x57, 0x27, 0x72, 0x54, 0x45, 0x41, 0x62, 0xee, 0x00, 0x36, 0xaa, 0x1f, 0xfa, 0xa3, 0xb0, 0x27, 0xeb, 0x3e, 0xf3, 0xcf, 0x04, 0x17, 0x68, 0x22, 0xf1, 0x1e, 0x1c, 0x9e, 0x27, 0x7d, 0x82, 0xb3, 0x3f, 0x3c, 0x12, 0x63, 0x94, 0x3b, 0xae, 0x87, 0x3c, 0x33, 0x6a, 0x08, 0x63, 0x84, 0xc2, 0xf8, 0x87, 0xbd, 0xfd, 0x25, 0x92, 0xb7, 0x8d, 0xdb, 0xac, 0xe9, 0xcb, 0x3f, 0x04, 0x3d, 0xee, 0x9f, 0xf6, 0x17, 0xbe, 0xea, 0x41, 0x7f, 0x2b, 0x2d, 0x4a, 0xbf, 0x64, 0xea, 0x01, 0x83, 0xf2, 0x59, 0x82, 0x6c, 0xcb, 0x6c, 0x1f, 0x91, 0x53, 0xde, 0x8a, 0x36, 0x7f, 0x41, 0x7e, 0x19, 0x02, 0x80, 0x42, 0x8c, 0xd5, 0xc1, 0x3c, 0x22, 0x06, 0xf4, 0x2d, 0x09, 0x45, 0xbf, 0xc1, 0x12, 0xe3, 0xfc, 0xa3, 0xc2, 0x89, 0x11, 0x7f, 0x01, 0xcb, 0x49, 0xab, 0xc1, 0x50, 0x37, 0xca, 0x03, 0xb7, 0x44, 0x94, 0x16, 0xbf, 0xd6, 0xf5, 0xa6, 0xbc, 0x10, 0x86, 0xf2, 0x97, 0xea, 0x66, 0x15, 0xa3, 0x9f, 0x4d, 0xf0, 0xe6, 0xa5, 0xfb, 0x1f, 0x25, 0xd7, 0x71, 0xed, 0x85, 0x53, 0x5b, 0x86, 0x1c, 0x46, 0x29, 0xb5, 0xa8, 0xa8, 0x25, 0x27, 0x5a, 0x51, 0x27, 0x30, 0xa7, 0x94, 0x07, 0x21, 0xf7, 0x66, 0xe2, 0xab, 0x16, 0x0e, 0x59, 0xa2, 0x7a, 0x70, 0x30, 0xba, 0x6b, 0x9f, 0xf9, 0x4d, 0x22, 0x4e, 0xa3, 0x33, 0x7e, 0x49, 0x43, 0x62, 0x29, 0xf5, 0xc7, 0x61, 0x7e, 0x5f, 0xcd, 0x02, 0x03, 0x01, 0x00, 0x01, 0x02, 0x82, 0x01, 0x00, 0x1e, 0x04, 0x4b, 0xc5, 0xa4, 0xa0, 0x8b, 0x1a, 0xfd, 0x3d, 0xbb, 0xce, 0x74, 0x6d, 0xdc, 0x8a, 0xc4, 0x8a, 0x7b, 0x49, 0xae, 0x98, 0xc8, 0xf2, 0xbc, 0xae, 0xd4, 0xd8, 0xa4, 0x61, 0x14, 0x03, 0x2c, 0xd9, 0xea, 0xb6, 0xae, 0xe5, 0xbc, 0xc8, 0x35, 0x11, 0x04, 0x9c, 0x41, 0xc2, 0x47, 0xd4, 0x2c, 0x9c, 0x0c, 0xdc, 0x1f, 0x8f, 0xc5, 0xa9, 0xd7, 0xb8, 0xd1, 0xb4, 0x12, 0xf2, 0x44, 0x71, 0x22, 0x69, 0x83, 0x47, 0x84, 0x04, 0x8c, 0x23, 0x37, 0x98, 0xf0, 0xbe, 0x7a, 0x67, 0x48, 0xd7, 0x32, 0xd2, 0xf5, 0x8d, 0xf1, 0xf1, 0x6e, 0xf4, 0x4b, 0xa5, 0x48, 0x1c, 0xcc, 0x7d, 0xe0, 0xa9, 0xee, 0x9d, 0xf3, 0x39, 0x77, 0x64, 0x91, 0x07, 0x70, 0x27, 0xf0, 0x34, 0xa2, 0x21, 0xd8, 0xec, 0xd0, 0xe7, 0xeb, 0x43, 0xc3, 0x6a, 0x20, 0x23, 0x10, 0xfe, 0x42, 0x02, 0x6b, 0xda, 0x89, 0xf4, 0x41, 0x96, 0x64, 0x32, 0x52, 0x20, 0x05, 0x0d, 0x5b, 0xf3, 0x67, 0x51, 0xb7, 0x7d, 0xd1, 0x24, 0x0b, 0x2c, 0x33, 0x84, 0x5b, 0xf9, 0xed, 0x66, 0xe6, 0x3c, 0x4d, 0xdf, 0x09, 0x3e, 0xd5, 0xe5, 0x1c, 0x27, 0x2c, 0x81, 0xee, 0x03, 0x91, 0x8d, 0xc0, 0x2b, 0x3e, 0xd9, 0x37, 0x8e, 0x3d, 0xd1, 0x30, 0xd6, 0x97, 0x7b, 0x98, 0xfb, 0x80, 0x13, 0x5a, 0x84, 0x08, 0x90, 0x0d, 0x5c, 0x99, 0x51, 0x4f, 0x8f, 0xab, 0x0c, 0x39, 0x69, 0x76, 0xf8, 0xf4, 0xfd, 0xa7, 0x04, 0x8d, 0x72, 0x27, 0xa6, 0x1e, 0xbd, 0xff, 0x10, 0x43, 0xe8, 0x53, 0xe7, 0x08, 0xb8, 0xbd, 0x55, 0xb4, 0x7a, 0xa2, 0x44, 0xe9, 0xe7, 0x78, 0xf7, 0x11, 0x49, 0x01, 0x70, 0x60, 0xdf, 0xe8, 0xd1, 0xb0, 0x8c, 0xa2, 0x3d, 0x98, 0x07, 0x9b, 0x66, 0xff, 0xe8, 0x68, 0x33, 0x82, 0xe3, 0x75, 0x3d, 0x37, 0x8d, 0xf2, 0x41, 0x02, 0x81, 0x81, 0x00, 0xe8, 0xc0, 0x12, 0x7f, 0x02, 0x98, 0x75, 0x23, 0xa6, 0x32, 0x92, 0x4e, 0x11, 0x27, 0xad, 0xda, 0x5b, 0x9e, 0xec, 0x9c, 0xa4, 0xb4, 0x26, 0x2b, 0x2b, 0xd4, 0xdb, 0x1a, 0x9e, 0xd5, 0xd3, 0xa8, 0xb4, 0x29, 0x58, 0x79, 0x96, 0x9f, 0x1a, 0xff, 0xdc, 0xef, 0x4c, 0xb3, 0x1b, 0x79, 0x36, 0xd3, 0x03, 0x4d, 0x08, 0x15, 0x54, 0xa7, 0x84, 0x2d, 0xc3, 0xb2, 0x44, 0x75, 0x15, 0x9f, 0x57, 0xae, 0x25, 0x64, 0xcc, 0x5f, 0xdf, 0x7d, 0xd3, 0xe9, 0xb7, 0xbc, 0xeb, 0x01, 0x92, 0xda, 0x9f, 0x7e, 0xc3, 0xc6, 0xce, 0xd9, 0xc2, 0x16, 0x5a, 0x52, 0x0c, 0x1e, 0xe2, 0x92, 0x4a, 0xf2, 0x33, 0x13, 0x78, 0x5f, 0xa3, 0xa8, 0x0d, 0x99, 0x75, 0x8d, 0x33, 0xd5, 0x71, 0xc6, 0x3c, 0x86, 0xf9, 0x36, 0xbf, 0x86, 0x2e, 0xc3, 0xfe, 0x63, 0x7d, 0x50, 0x94, 0xb6, 0x71, 0x7f, 0x9f, 0xb6, 0x55, 0xa5, 0x02, 0x81, 0x81, 0x00, 0xd0, 0xa6, 0xcd, 0xaf, 0x92, 0x3b, 0x7a, 0x2f, 0x17, 0xfd, 0xd1, 0x05, 0x6b, 0x9c, 0x95, 0xb7, 0x7b, 0x39, 0x0c, 0xa5, 0xde, 0xb1, 0xa4, 0x86, 0x87, 0x39, 0x73, 0xb0, 0x22, 0xb3, 0x7c, 0x6a, 0x14, 0xdc, 0x19, 0x98, 0xa7, 0xe7, 0x02, 0xdb, 0x54, 0xa0, 0xc3, 0xbc, 0x80, 0x54, 0x60, 0xb6, 0xa6, 0xf4, 0xc5, 0x01, 0xe1, 0xc3, 0xf7, 0xc3, 0xd2, 0xdb, 0xe7, 0x1f, 0xc9, 0xcc, 0x51, 0x66, 0x66, 0xd0, 0xce, 0x31, 0x5a, 0x31, 0x76, 0xb7, 0x98, 0x52, 0xda, 0x82, 0xe8, 0x33, 0xc8, 0xf0, 0x1a, 0x8f, 0x95, 0x46, 0x7f, 0x48, 0x72, 0x47, 0x1e, 0x33, 0x3c, 0x0f, 0xd7, 0x55, 0x21, 0xc3, 0xea, 0x10, 0x8e, 0xae, 0xbc, 0x18, 0xa5, 0xcc, 0x85, 0xf1, 0x09, 0x3d, 0x15, 0x82, 0xa0, 0x49, 0x55, 0xd6, 0x7f, 0x64, 0xe0, 0xb0, 0xf0, 0x17, 0x75, 0xbd, 0x92, 0xc7, 0x83, 0xe3, 0x59, 0x09, 0x02, 0x81, 0x81, 0x00, 0x88, 0x6b, 0xd4, 0x2b, 0x87, 0xcc, 0xee, 0x93, 0xe7, 0x9d, 0x2a, 0xae, 0x01, 0x56, 0x1d, 0x8b, 0xa8, 0x3a, 0x1d, 0x7b, 0xae, 0xfa, 0x3c, 0x88, 0xff, 0x56, 0xf2, 0xd9, 0xc6, 0x91, 0x94, 0x4f, 0x04, 0xd2, 0x5b, 0x1e, 0x61, 0x4f, 0x7e, 0x96, 0xcb, 0xdb, 0xa3, 0x3c, 0x33, 0xf5, 0x37, 0x52, 0x35, 0x54, 0x18, 0x51, 0xd0, 0x5d, 0xa3, 0x96, 0xe3, 0x66, 0x80, 0xc3, 0x93, 0xd9, 0xe2, 0x9d, 0x9b, 0x23, 0x5a, 0xbb, 0x33, 0x16, 0xe0, 0x77, 0xd4, 0x0f, 0x32, 0x3b, 0xa8, 0xe4, 0xe5, 0xa9, 0x7a, 0x7c, 0xf3, 0xcf, 0x24, 0xf8, 0xcf, 0x15, 0xda, 0x2e, 0xdc, 0x24, 0x5d, 0x33, 0x5b, 0x06, 0xa5, 0x7e, 0x81, 0x41, 0x46, 0x3f, 0x55, 0x6c, 0x5f, 0x1e, 0x53, 0x62, 0x9b, 0x25, 0x8d, 0xbb, 0x2e, 0x45, 0x2a, 0xf2, 0x0c, 0x10, 0x2a, 0x6a, 0x69, 0xd0, 0x09, 0xf4, 0x81, 0x1b, 0x71, 0x55, 0x02, 0x81, 0x80, 0x66, 0x63, 0x74, 0x4b, 0xd3, 0xd6, 0x9b, 0xfe, 0xc0, 0x27, 0x2d, 0x8b, 0x1b, 0x63, 0x9b, 0x94, 0x8e, 0x43, 0x50, 0x91, 0x94, 0xd6, 0x57, 0x86, 0x2c, 0x95, 0x64, 0xcf, 0xea, 0x37, 0x69, 0xb6, 0x24, 0xc6, 0x5d, 0x49, 0x2c, 0x1b, 0x90, 0xab, 0x50, 0xbc, 0x13, 0x51, 0x4d, 0x28, 0x1a, 0xcd, 0x86, 0xe0, 0x56, 0x4c, 0xb6, 0x1d, 0x14, 0x58, 0x64, 0x00, 0xc5, 0x4a, 0x34, 0x1c, 0xaf, 0x55, 0x30, 0xdf, 0x06, 0x4f, 0xf1, 0x92, 0x94, 0x4f, 0x43, 0xd0, 0x64, 0xaa, 0x18, 0x88, 0x50, 0xf2, 0x82, 0x16, 0x33, 0x8a, 0x84, 0xab, 0x68, 0x68, 0xbd, 0xc9, 0x26, 0x90, 0x1f, 0x7b, 0x07, 0x36, 0xbc, 0x85, 0xa3, 0x7e, 0xdb, 0x8e, 0xbc, 0xcd, 0xc0, 0x6c, 0xa7, 0xbb, 0xf1, 0xf2, 0x47, 0xf5, 0xb4, 0xc9, 0xad, 0x7a, 0x33, 0x48, 0xa0, 0x88, 0xe2, 0x9e, 0x44, 0x88, 0xe3, 0x8f, 0x8d, 0x01, 0x02, 0x81, 0x80, 0x04, 0xa3, 0xe0, 0xb3, 0x7e, 0xdd, 0x12, 0x94, 0x27, 0xb0, 0xac, 0x4b, 0x26, 0xfd, 0xb2, 0x5f, 0x2b, 0x91, 0x29, 0x5a, 0x0b, 0x2b, 0x9a, 0xeb, 0x08, 0x21, 0xde, 0x15, 0x79, 0x8a, 0x55, 0x0c, 0xec, 0xac, 0x85, 0x72, 0x11, 0xb6, 0x1d, 0x51, 0xf1, 0xa6, 0x28, 0xa0, 0x86, 0xae, 0x23, 0x7c, 0x4c, 0x2c, 0xfe, 0xce, 0xd4, 0xd3, 0xf2, 0x67, 0x47, 0x6c, 0xa7, 0xfd, 0xe6, 0x80, 0x4f, 0x8d, 0x54, 0xa9, 0x8a, 0xb8, 0x80, 0xc5, 0xbc, 0x6b, 0x7e, 0xe1, 0xc2, 0xa1, 0x24, 0xcf, 0x2d, 0xe1, 0x0c, 0x9f, 0x7b, 0x71, 0xcf, 0x75, 0xb2, 0x04, 0xf8, 0x51, 0xac, 0x07, 0x10, 0x56, 0x93, 0x46, 0x92, 0xdd, 0x1d, 0x5b, 0x1f, 0x94, 0x87, 0xcf, 0xe2, 0x99, 0x36, 0x89, 0xe7, 0xc2, 0x8a, 0x0a, 0x9e, 0x0d, 0x30, 0x17, 0xd5, 0x6d, 0xde, 0x10, 0x94, 0x47, 0x35, 0x89, 0x10, 0xe6, 0x8c, 0x0e};

    u8_t cert[] = {0x30, 0x82, 0x03, 0x6b, 0x30, 0x82, 0x02, 0x53, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x14, 0x72, 0x8e, 0xfd, 0x0e, 0x52, 0x0a, 0x87, 0xdd, 0x55, 0x25, 0xee, 0x05, 0x11, 0x1d, 0x0d, 0xf7, 0xc8, 0x64, 0x5b, 0xa0, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x45, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x41, 0x55, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x08, 0x49, 0x4f, 0x20, 0x50, 0x72, 0x65, 0x73, 0x73, 0x31, 0x0e, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x05, 0x50, 0x69, 0x63, 0x6f, 0x57, 0x30, 0x1e, 0x17, 0x0d, 0x32, 0x33, 0x30, 0x32, 0x30, 0x36, 0x31, 0x35, 0x30, 0x39, 0x35, 0x34, 0x5a, 0x17, 0x0d, 0x32, 0x34, 0x30, 0x32, 0x30, 0x36, 0x31, 0x35, 0x30, 0x39, 0x35, 0x34, 0x5a, 0x30, 0x45, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x41, 0x55, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x08, 0x49, 0x4f, 0x20, 0x50, 0x72, 0x65, 0x73, 0x73, 0x31, 0x0e, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x05, 0x50, 0x69, 0x63, 0x6f, 0x57, 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbd, 0xb3, 0xb6, 0x94, 0x9f, 0x87, 0x85, 0xd6, 0xd4, 0xd0, 0xf9, 0x24, 0x4b, 0x8c, 0x7d, 0x9e, 0xf5, 0x83, 0xac, 0x90, 0x37, 0x5b, 0xdf, 0x4d, 0x9b, 0x05, 0x6b, 0x5f, 0xaa, 0x87, 0x31, 0x87, 0x0e, 0x97, 0x90, 0xa0, 0xff, 0x12, 0x81, 0xcc, 0xfe, 0x66, 0xa3, 0x8e, 0x34, 0x33, 0x63, 0x27, 0x10, 0xa4, 0xf1, 0x57, 0x27, 0x72, 0x54, 0x45, 0x41, 0x62, 0xee, 0x00, 0x36, 0xaa, 0x1f, 0xfa, 0xa3, 0xb0, 0x27, 0xeb, 0x3e, 0xf3, 0xcf, 0x04, 0x17, 0x68, 0x22, 0xf1, 0x1e, 0x1c, 0x9e, 0x27, 0x7d, 0x82, 0xb3, 0x3f, 0x3c, 0x12, 0x63, 0x94, 0x3b, 0xae, 0x87, 0x3c, 0x33, 0x6a, 0x08, 0x63, 0x84, 0xc2, 0xf8, 0x87, 0xbd, 0xfd, 0x25, 0x92, 0xb7, 0x8d, 0xdb, 0xac, 0xe9, 0xcb, 0x3f, 0x04, 0x3d, 0xee, 0x9f, 0xf6, 0x17, 0xbe, 0xea, 0x41, 0x7f, 0x2b, 0x2d, 0x4a, 0xbf, 0x64, 0xea, 0x01, 0x83, 0xf2, 0x59, 0x82, 0x6c, 0xcb, 0x6c, 0x1f, 0x91, 0x53, 0xde, 0x8a, 0x36, 0x7f, 0x41, 0x7e, 0x19, 0x02, 0x80, 0x42, 0x8c, 0xd5, 0xc1, 0x3c, 0x22, 0x06, 0xf4, 0x2d, 0x09, 0x45, 0xbf, 0xc1, 0x12, 0xe3, 0xfc, 0xa3, 0xc2, 0x89, 0x11, 0x7f, 0x01, 0xcb, 0x49, 0xab, 0xc1, 0x50, 0x37, 0xca, 0x03, 0xb7, 0x44, 0x94, 0x16, 0xbf, 0xd6, 0xf5, 0xa6, 0xbc, 0x10, 0x86, 0xf2, 0x97, 0xea, 0x66, 0x15, 0xa3, 0x9f, 0x4d, 0xf0, 0xe6, 0xa5, 0xfb, 0x1f, 0x25, 0xd7, 0x71, 0xed, 0x85, 0x53, 0x5b, 0x86, 0x1c, 0x46, 0x29, 0xb5, 0xa8, 0xa8, 0x25, 0x27, 0x5a, 0x51, 0x27, 0x30, 0xa7, 0x94, 0x07, 0x21, 0xf7, 0x66, 0xe2, 0xab, 0x16, 0x0e, 0x59, 0xa2, 0x7a, 0x70, 0x30, 0xba, 0x6b, 0x9f, 0xf9, 0x4d, 0x22, 0x4e, 0xa3, 0x33, 0x7e, 0x49, 0x43, 0x62, 0x29, 0xf5, 0xc7, 0x61, 0x7e, 0x5f, 0xcd, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x53, 0x30, 0x51, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x93, 0xc8, 0x8f, 0xac, 0x37, 0x01, 0x7e, 0x4d, 0xd2, 0x87, 0x7a, 0xb5, 0x26, 0xba, 0xd1, 0xa6, 0x1a, 0xcd, 0xd1, 0xb2, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x93, 0xc8, 0x8f, 0xac, 0x37, 0x01, 0x7e, 0x4d, 0xd2, 0x87, 0x7a, 0xb5, 0x26, 0xba, 0xd1, 0xa6, 0x1a, 0xcd, 0xd1, 0xb2, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05, 0x30, 0x03, 0x01, 0x01, 0xff, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x01, 0x01, 0x00, 0x5b, 0x91, 0x51, 0xe1, 0x89, 0x20, 0xf5, 0xdf, 0x02, 0x94, 0x59, 0x76, 0x9e, 0xdc, 0x53, 0xf3, 0x17, 0x8f, 0x96, 0x17, 0xd1, 0x2f, 0x65, 0x36, 0xd4, 0x56, 0x7e, 0xd8, 0x0d, 0x7e, 0x59, 0x79, 0xab, 0x47, 0x67, 0x01, 0xb6, 0x9e, 0xf6, 0x7a, 0x0d, 0x20, 0xd2, 0xb2, 0x2d, 0x87, 0x84, 0x07, 0x40, 0x2d, 0x83, 0x1e, 0x16, 0x4f, 0x2d, 0x20, 0xaf, 0xf2, 0xca, 0xde, 0x10, 0x73, 0x41, 0xb9, 0x48, 0x3c, 0x4f, 0x9d, 0x55, 0xbc, 0xee, 0x68, 0xae, 0x66, 0x4d, 0x5d, 0x41, 0xa9, 0xbc, 0x51, 0x6d, 0xe2, 0x37, 0x0c, 0x0f, 0xf4, 0x43, 0xa0, 0x84, 0xf9, 0x40, 0xbc, 0x89, 0xaa, 0xcd, 0x14, 0xb4, 0xd5, 0xda, 0xd1, 0xb3, 0x2c, 0x4a, 0x56, 0x7e, 0x86, 0x2c, 0x71, 0xaa, 0x75, 0x86, 0x48, 0x14, 0x2a, 0xbc, 0x05, 0xab, 0x14, 0x72, 0x72, 0x01, 0xc8, 0xff, 0x02, 0x3d, 0x2e, 0xe9, 0xef, 0x21, 0x4d, 0x71, 0xf3, 0x0c, 0xba, 0x40, 0xfd, 0x9f, 0xb1, 0x40, 0xea, 0x47, 0x65, 0x3d, 0xb7, 0x52, 0xd8, 0xbb, 0x13, 0x30, 0x38, 0xb4, 0x3c, 0xbf, 0x76, 0x06, 0xe2, 0xb3, 0x3f, 0xf7, 0x7b, 0xdd, 0xdf, 0x54, 0x7b, 0x8d, 0x0c, 0x4d, 0x4a, 0x96, 0xcd, 0x14, 0x5c, 0x7d, 0xed, 0xb3, 0x2f, 0xbd, 0x27, 0xc8, 0x52, 0x6e, 0x58, 0x8e, 0x9c, 0x07, 0xa1, 0x52, 0xe2, 0x49, 0x8c, 0x04, 0x3f, 0x84, 0x32, 0x7b, 0xff, 0x5f, 0xf4, 0xf2, 0xdf, 0x3c, 0x73, 0xff, 0x9f, 0x63, 0x0e, 0xe5, 0x7f, 0xdf, 0xa8, 0x7e, 0x4d, 0xf3, 0x29, 0xd8, 0x2b, 0x41, 0x25, 0xbc, 0x73, 0x41, 0x3b, 0x1f, 0x39, 0x64, 0x48, 0x85, 0xe5, 0x66, 0x90, 0x8c, 0xd3, 0x8a, 0xce, 0xdc, 0xb5, 0x0d, 0x93, 0xb0, 0xd0, 0x8a, 0xef, 0x74, 0x8f, 0x28, 0x2f, 0x2c, 0x96, 0x4a, 0x4f, 0xc3, 0xf1, 0xde, 0x25, 0xff, 0xd4};
    struct altcp_tls_config *tls_config = altcp_tls_create_config_server_privkey_cert(key, sizeof(key), NULL, 0, cert, sizeof(cert));
    struct altcp_pcb *pcb = altcp_tls_new(tls_config, IPADDR_TYPE_ANY);

    altcp_accept(pcb, accept);

    altcp_bind(pcb, IP_ADDR_ANY, 443);
    cyw43_arch_lwip_begin();
    pcb = altcp_listen_with_backlog(pcb, 3);
    cyw43_arch_lwip_end();
    while (true)
    {
        sleep_ms(500);
    }
}

Page 137 Full listing not in book

Simple HTTPS Server lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define LWIP_ALTCP               1
#define LWIP_ALTCP_TLS           1
#define LWIP_ALTCP_TLS_MBEDTLS   1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG  LWIP_DBG_ON
#define TCP_LISTEN_BACKLOG       1
#endif /* __LWIPOPTS_H__ */

Page 137 Full listing not in book

Simple HTTPS Server mbedtls_config.h

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C

//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES
#define MBEDTLS_GCM_C

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client and server modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION

#define MBEDTLS_SSL_SRV_C

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 137 Full listing not in book

Simple HTTPS Server CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
 main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background hardware_rtc pico_lwip_mbedtls pico_mbedtls)
pico_add_extra_outputs(main)

Page 140 Simple HTTP Bultin Server Main Program  

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/apps/httpd.h"
#include "setupWifi.h"

int main()
{
    stdio_init_all();
    connect();

    httpd_init();

    while (true)
    {
        sleep_ms(500);
    }
}

Page 140 Full listing not in book

Simple HTTP Bultin Server Cmakelists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_http)
pico_add_extra_outputs(main)

Page 140 Full listing not in book

Simple HTTP Bultin Server lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND 16384

#define LWIP_ALTCP 1

#define LWIP_DEBUG 1
#define TCP_LISTEN_BACKLOG 1

#endif /* __LWIPOPTS_H__ */

Page 141 Linux Cmakelists.txt for htmlgen

cmake_minimum_required(VERSION 3.13)
project(makefsdata C CXX ASM)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

add_executable(htmlgen
 makefsdata.c
)

target_include_directories(htmlgen
         PRIVATE ../../../../src/include/
         PRIVATE ../../../../contrib/ports/unix/port/include/
         PRIVATE ${CMAKE_CURRENT_LIST_DIR})

Page 141 Windows Cmakelists.txt for htmlgen

cmake_minimum_required(VERSION 3.13)

project(makefsdata C CXX ASM)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

add_executable(htmlgen
 makefsdata.c
)

target_include_directories(htmlgen
         PRIVATE ../../../../src/include/

         PRIVATE ../../../../contrib/ports/win32/include/

         PRIVATE ${CMAKE_CURRENT_LIST_DIR})

Page 151

Simple HTTPS Bultin Server Main Program TLS and SSI

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/altcp_tls.h"

#include "lwip/apps/httpd.h"
#include "hardware/structs/rosc.h"

#include "hardware/rtc.h"
#include "time.h"

#include "setupWifi.h"

#define BUF_SIZE 2048





void getDateNow(struct tm *t)
{
    datetime_t rtc;
    rtc_get_datetime(&rtc);

    t->tm_sec = rtc.sec;
    t->tm_min = rtc.min;
    t->tm_hour = rtc.hour;
    t->tm_mday = rtc.day;
    t->tm_mon = rtc.month - 1;
    t->tm_year = rtc.year - 1900;
    t->tm_wday = rtc.dotw;
    t->tm_yday = 0;
    t->tm_isdst = -1;
}

void setRTC()
{
    datetime_t t = {
        .year = 2023,
        .month = 02,
        .day = 05,
        .dotw = 0,
        .hour = 6,
        .min = 14,
        .sec = 00};
    rtc_init();
    rtc_set_datetime(&t);
}

const char *ssitags[] = {"temp", "hum"};

u16_t mySSIHandler(int iIndex, char *pcInsert, int iInsertLen)
{
    switch(iIndex){
        case 0:
            snprintf(pcInsert, iInsertLen, "42 C");
            break;
        case 1:
            snprintf(pcInsert, iInsertLen, "80%%");
            break;
    }
}

int main()
{
    stdio_init_all();
    setRTC();
    connect();


    u8_t key[] = {0x30, 0x82, 0x04, 0xbd, 0x02, 0x01, 0x00, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x04, 0x82, 0x04, 0xa7, 0x30, 0x82, 0x04, 0xa3, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbd, 0xb3, 0xb6, 0x94, 0x9f, 0x87, 0x85, 0xd6, 0xd4, 0xd0, 0xf9, 0x24, 0x4b, 0x8c, 0x7d, 0x9e, 0xf5, 0x83, 0xac, 0x90, 0x37, 0x5b, 0xdf, 0x4d, 0x9b, 0x05, 0x6b, 0x5f, 0xaa, 0x87, 0x31, 0x87, 0x0e, 0x97, 0x90, 0xa0, 0xff, 0x12, 0x81, 0xcc, 0xfe, 0x66, 0xa3, 0x8e, 0x34, 0x33, 0x63, 0x27, 0x10, 0xa4, 0xf1, 0x57, 0x27, 0x72, 0x54, 0x45, 0x41, 0x62, 0xee, 0x00, 0x36, 0xaa, 0x1f, 0xfa, 0xa3, 0xb0, 0x27, 0xeb, 0x3e, 0xf3, 0xcf, 0x04, 0x17, 0x68, 0x22, 0xf1, 0x1e, 0x1c, 0x9e, 0x27, 0x7d, 0x82, 0xb3, 0x3f, 0x3c, 0x12, 0x63, 0x94, 0x3b, 0xae, 0x87, 0x3c, 0x33, 0x6a, 0x08, 0x63, 0x84, 0xc2, 0xf8, 0x87, 0xbd, 0xfd, 0x25, 0x92, 0xb7, 0x8d, 0xdb, 0xac, 0xe9, 0xcb, 0x3f, 0x04, 0x3d, 0xee, 0x9f, 0xf6, 0x17, 0xbe, 0xea, 0x41, 0x7f, 0x2b, 0x2d, 0x4a, 0xbf, 0x64, 0xea, 0x01, 0x83, 0xf2, 0x59, 0x82, 0x6c, 0xcb, 0x6c, 0x1f, 0x91, 0x53, 0xde, 0x8a, 0x36, 0x7f, 0x41, 0x7e, 0x19, 0x02, 0x80, 0x42, 0x8c, 0xd5, 0xc1, 0x3c, 0x22, 0x06, 0xf4, 0x2d, 0x09, 0x45, 0xbf, 0xc1, 0x12, 0xe3, 0xfc, 0xa3, 0xc2, 0x89, 0x11, 0x7f, 0x01, 0xcb, 0x49, 0xab, 0xc1, 0x50, 0x37, 0xca, 0x03, 0xb7, 0x44, 0x94, 0x16, 0xbf, 0xd6, 0xf5, 0xa6, 0xbc, 0x10, 0x86, 0xf2, 0x97, 0xea, 0x66, 0x15, 0xa3, 0x9f, 0x4d, 0xf0, 0xe6, 0xa5, 0xfb, 0x1f, 0x25, 0xd7, 0x71, 0xed, 0x85, 0x53, 0x5b, 0x86, 0x1c, 0x46, 0x29, 0xb5, 0xa8, 0xa8, 0x25, 0x27, 0x5a, 0x51, 0x27, 0x30, 0xa7, 0x94, 0x07, 0x21, 0xf7, 0x66, 0xe2, 0xab, 0x16, 0x0e, 0x59, 0xa2, 0x7a, 0x70, 0x30, 0xba, 0x6b, 0x9f, 0xf9, 0x4d, 0x22, 0x4e, 0xa3, 0x33, 0x7e, 0x49, 0x43, 0x62, 0x29, 0xf5, 0xc7, 0x61, 0x7e, 0x5f, 0xcd, 0x02, 0x03, 0x01, 0x00, 0x01, 0x02, 0x82, 0x01, 0x00, 0x1e, 0x04, 0x4b, 0xc5, 0xa4, 0xa0, 0x8b, 0x1a, 0xfd, 0x3d, 0xbb, 0xce, 0x74, 0x6d, 0xdc, 0x8a, 0xc4, 0x8a, 0x7b, 0x49, 0xae, 0x98, 0xc8, 0xf2, 0xbc, 0xae, 0xd4, 0xd8, 0xa4, 0x61, 0x14, 0x03, 0x2c, 0xd9, 0xea, 0xb6, 0xae, 0xe5, 0xbc, 0xc8, 0x35, 0x11, 0x04, 0x9c, 0x41, 0xc2, 0x47, 0xd4, 0x2c, 0x9c, 0x0c, 0xdc, 0x1f, 0x8f, 0xc5, 0xa9, 0xd7, 0xb8, 0xd1, 0xb4, 0x12, 0xf2, 0x44, 0x71, 0x22, 0x69, 0x83, 0x47, 0x84, 0x04, 0x8c, 0x23, 0x37, 0x98, 0xf0, 0xbe, 0x7a, 0x67, 0x48, 0xd7, 0x32, 0xd2, 0xf5, 0x8d, 0xf1, 0xf1, 0x6e, 0xf4, 0x4b, 0xa5, 0x48, 0x1c, 0xcc, 0x7d, 0xe0, 0xa9, 0xee, 0x9d, 0xf3, 0x39, 0x77, 0x64, 0x91, 0x07, 0x70, 0x27, 0xf0, 0x34, 0xa2, 0x21, 0xd8, 0xec, 0xd0, 0xe7, 0xeb, 0x43, 0xc3, 0x6a, 0x20, 0x23, 0x10, 0xfe, 0x42, 0x02, 0x6b, 0xda, 0x89, 0xf4, 0x41, 0x96, 0x64, 0x32, 0x52, 0x20, 0x05, 0x0d, 0x5b, 0xf3, 0x67, 0x51, 0xb7, 0x7d, 0xd1, 0x24, 0x0b, 0x2c, 0x33, 0x84, 0x5b, 0xf9, 0xed, 0x66, 0xe6, 0x3c, 0x4d, 0xdf, 0x09, 0x3e, 0xd5, 0xe5, 0x1c, 0x27, 0x2c, 0x81, 0xee, 0x03, 0x91, 0x8d, 0xc0, 0x2b, 0x3e, 0xd9, 0x37, 0x8e, 0x3d, 0xd1, 0x30, 0xd6, 0x97, 0x7b, 0x98, 0xfb, 0x80, 0x13, 0x5a, 0x84, 0x08, 0x90, 0x0d, 0x5c, 0x99, 0x51, 0x4f, 0x8f, 0xab, 0x0c, 0x39, 0x69, 0x76, 0xf8, 0xf4, 0xfd, 0xa7, 0x04, 0x8d, 0x72, 0x27, 0xa6, 0x1e, 0xbd, 0xff, 0x10, 0x43, 0xe8, 0x53, 0xe7, 0x08, 0xb8, 0xbd, 0x55, 0xb4, 0x7a, 0xa2, 0x44, 0xe9, 0xe7, 0x78, 0xf7, 0x11, 0x49, 0x01, 0x70, 0x60, 0xdf, 0xe8, 0xd1, 0xb0, 0x8c, 0xa2, 0x3d, 0x98, 0x07, 0x9b, 0x66, 0xff, 0xe8, 0x68, 0x33, 0x82, 0xe3, 0x75, 0x3d, 0x37, 0x8d, 0xf2, 0x41, 0x02, 0x81, 0x81, 0x00, 0xe8, 0xc0, 0x12, 0x7f, 0x02, 0x98, 0x75, 0x23, 0xa6, 0x32, 0x92, 0x4e, 0x11, 0x27, 0xad, 0xda, 0x5b, 0x9e, 0xec, 0x9c, 0xa4, 0xb4, 0x26, 0x2b, 0x2b, 0xd4, 0xdb, 0x1a, 0x9e, 0xd5, 0xd3, 0xa8, 0xb4, 0x29, 0x58, 0x79, 0x96, 0x9f, 0x1a, 0xff, 0xdc, 0xef, 0x4c, 0xb3, 0x1b, 0x79, 0x36, 0xd3, 0x03, 0x4d, 0x08, 0x15, 0x54, 0xa7, 0x84, 0x2d, 0xc3, 0xb2, 0x44, 0x75, 0x15, 0x9f, 0x57, 0xae, 0x25, 0x64, 0xcc, 0x5f, 0xdf, 0x7d, 0xd3, 0xe9, 0xb7, 0xbc, 0xeb, 0x01, 0x92, 0xda, 0x9f, 0x7e, 0xc3, 0xc6, 0xce, 0xd9, 0xc2, 0x16, 0x5a, 0x52, 0x0c, 0x1e, 0xe2, 0x92, 0x4a, 0xf2, 0x33, 0x13, 0x78, 0x5f, 0xa3, 0xa8, 0x0d, 0x99, 0x75, 0x8d, 0x33, 0xd5, 0x71, 0xc6, 0x3c, 0x86, 0xf9, 0x36, 0xbf, 0x86, 0x2e, 0xc3, 0xfe, 0x63, 0x7d, 0x50, 0x94, 0xb6, 0x71, 0x7f, 0x9f, 0xb6, 0x55, 0xa5, 0x02, 0x81, 0x81, 0x00, 0xd0, 0xa6, 0xcd, 0xaf, 0x92, 0x3b, 0x7a, 0x2f, 0x17, 0xfd, 0xd1, 0x05, 0x6b, 0x9c, 0x95, 0xb7, 0x7b, 0x39, 0x0c, 0xa5, 0xde, 0xb1, 0xa4, 0x86, 0x87, 0x39, 0x73, 0xb0, 0x22, 0xb3, 0x7c, 0x6a, 0x14, 0xdc, 0x19, 0x98, 0xa7, 0xe7, 0x02, 0xdb, 0x54, 0xa0, 0xc3, 0xbc, 0x80, 0x54, 0x60, 0xb6, 0xa6, 0xf4, 0xc5, 0x01, 0xe1, 0xc3, 0xf7, 0xc3, 0xd2, 0xdb, 0xe7, 0x1f, 0xc9, 0xcc, 0x51, 0x66, 0x66, 0xd0, 0xce, 0x31, 0x5a, 0x31, 0x76, 0xb7, 0x98, 0x52, 0xda, 0x82, 0xe8, 0x33, 0xc8, 0xf0, 0x1a, 0x8f, 0x95, 0x46, 0x7f, 0x48, 0x72, 0x47, 0x1e, 0x33, 0x3c, 0x0f, 0xd7, 0x55, 0x21, 0xc3, 0xea, 0x10, 0x8e, 0xae, 0xbc, 0x18, 0xa5, 0xcc, 0x85, 0xf1, 0x09, 0x3d, 0x15, 0x82, 0xa0, 0x49, 0x55, 0xd6, 0x7f, 0x64, 0xe0, 0xb0, 0xf0, 0x17, 0x75, 0xbd, 0x92, 0xc7, 0x83, 0xe3, 0x59, 0x09, 0x02, 0x81, 0x81, 0x00, 0x88, 0x6b, 0xd4, 0x2b, 0x87, 0xcc, 0xee, 0x93, 0xe7, 0x9d, 0x2a, 0xae, 0x01, 0x56, 0x1d, 0x8b, 0xa8, 0x3a, 0x1d, 0x7b, 0xae, 0xfa, 0x3c, 0x88, 0xff, 0x56, 0xf2, 0xd9, 0xc6, 0x91, 0x94, 0x4f, 0x04, 0xd2, 0x5b, 0x1e, 0x61, 0x4f, 0x7e, 0x96, 0xcb, 0xdb, 0xa3, 0x3c, 0x33, 0xf5, 0x37, 0x52, 0x35, 0x54, 0x18, 0x51, 0xd0, 0x5d, 0xa3, 0x96, 0xe3, 0x66, 0x80, 0xc3, 0x93, 0xd9, 0xe2, 0x9d, 0x9b, 0x23, 0x5a, 0xbb, 0x33, 0x16, 0xe0, 0x77, 0xd4, 0x0f, 0x32, 0x3b, 0xa8, 0xe4, 0xe5, 0xa9, 0x7a, 0x7c, 0xf3, 0xcf, 0x24, 0xf8, 0xcf, 0x15, 0xda, 0x2e, 0xdc, 0x24, 0x5d, 0x33, 0x5b, 0x06, 0xa5, 0x7e, 0x81, 0x41, 0x46, 0x3f, 0x55, 0x6c, 0x5f, 0x1e, 0x53, 0x62, 0x9b, 0x25, 0x8d, 0xbb, 0x2e, 0x45, 0x2a, 0xf2, 0x0c, 0x10, 0x2a, 0x6a, 0x69, 0xd0, 0x09, 0xf4, 0x81, 0x1b, 0x71, 0x55, 0x02, 0x81, 0x80, 0x66, 0x63, 0x74, 0x4b, 0xd3, 0xd6, 0x9b, 0xfe, 0xc0, 0x27, 0x2d, 0x8b, 0x1b, 0x63, 0x9b, 0x94, 0x8e, 0x43, 0x50, 0x91, 0x94, 0xd6, 0x57, 0x86, 0x2c, 0x95, 0x64, 0xcf, 0xea, 0x37, 0x69, 0xb6, 0x24, 0xc6, 0x5d, 0x49, 0x2c, 0x1b, 0x90, 0xab, 0x50, 0xbc, 0x13, 0x51, 0x4d, 0x28, 0x1a, 0xcd, 0x86, 0xe0, 0x56, 0x4c, 0xb6, 0x1d, 0x14, 0x58, 0x64, 0x00, 0xc5, 0x4a, 0x34, 0x1c, 0xaf, 0x55, 0x30, 0xdf, 0x06, 0x4f, 0xf1, 0x92, 0x94, 0x4f, 0x43, 0xd0, 0x64, 0xaa, 0x18, 0x88, 0x50, 0xf2, 0x82, 0x16, 0x33, 0x8a, 0x84, 0xab, 0x68, 0x68, 0xbd, 0xc9, 0x26, 0x90, 0x1f, 0x7b, 0x07, 0x36, 0xbc, 0x85, 0xa3, 0x7e, 0xdb, 0x8e, 0xbc, 0xcd, 0xc0, 0x6c, 0xa7, 0xbb, 0xf1, 0xf2, 0x47, 0xf5, 0xb4, 0xc9, 0xad, 0x7a, 0x33, 0x48, 0xa0, 0x88, 0xe2, 0x9e, 0x44, 0x88, 0xe3, 0x8f, 0x8d, 0x01, 0x02, 0x81, 0x80, 0x04, 0xa3, 0xe0, 0xb3, 0x7e, 0xdd, 0x12, 0x94, 0x27, 0xb0, 0xac, 0x4b, 0x26, 0xfd, 0xb2, 0x5f, 0x2b, 0x91, 0x29, 0x5a, 0x0b, 0x2b, 0x9a, 0xeb, 0x08, 0x21, 0xde, 0x15, 0x79, 0x8a, 0x55, 0x0c, 0xec, 0xac, 0x85, 0x72, 0x11, 0xb6, 0x1d, 0x51, 0xf1, 0xa6, 0x28, 0xa0, 0x86, 0xae, 0x23, 0x7c, 0x4c, 0x2c, 0xfe, 0xce, 0xd4, 0xd3, 0xf2, 0x67, 0x47, 0x6c, 0xa7, 0xfd, 0xe6, 0x80, 0x4f, 0x8d, 0x54, 0xa9, 0x8a, 0xb8, 0x80, 0xc5, 0xbc, 0x6b, 0x7e, 0xe1, 0xc2, 0xa1, 0x24, 0xcf, 0x2d, 0xe1, 0x0c, 0x9f, 0x7b, 0x71, 0xcf, 0x75, 0xb2, 0x04, 0xf8, 0x51, 0xac, 0x07, 0x10, 0x56, 0x93, 0x46, 0x92, 0xdd, 0x1d, 0x5b, 0x1f, 0x94, 0x87, 0xcf, 0xe2, 0x99, 0x36, 0x89, 0xe7, 0xc2, 0x8a, 0x0a, 0x9e, 0x0d, 0x30, 0x17, 0xd5, 0x6d, 0xde, 0x10, 0x94, 0x47, 0x35, 0x89, 0x10, 0xe6, 0x8c, 0x0e};
    u8_t cert[] = {0x30, 0x82, 0x03, 0x6b, 0x30, 0x82, 0x02, 0x53, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x14, 0x72, 0x8e, 0xfd, 0x0e, 0x52, 0x0a, 0x87, 0xdd, 0x55, 0x25, 0xee, 0x05, 0x11, 0x1d, 0x0d, 0xf7, 0xc8, 0x64, 0x5b, 0xa0, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x45, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x41, 0x55, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x08, 0x49, 0x4f, 0x20, 0x50, 0x72, 0x65, 0x73, 0x73, 0x31, 0x0e, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x05, 0x50, 0x69, 0x63, 0x6f, 0x57, 0x30, 0x1e, 0x17, 0x0d, 0x32, 0x33, 0x30, 0x32, 0x30, 0x36, 0x31, 0x35, 0x30, 0x39, 0x35, 0x34, 0x5a, 0x17, 0x0d, 0x32, 0x34, 0x30, 0x32, 0x30, 0x36, 0x31, 0x35, 0x30, 0x39, 0x35, 0x34, 0x5a, 0x30, 0x45, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x41, 0x55, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x08, 0x49, 0x4f, 0x20, 0x50, 0x72, 0x65, 0x73, 0x73, 0x31, 0x0e, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x05, 0x50, 0x69, 0x63, 0x6f, 0x57, 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbd, 0xb3, 0xb6, 0x94, 0x9f, 0x87, 0x85, 0xd6, 0xd4, 0xd0, 0xf9, 0x24, 0x4b, 0x8c, 0x7d, 0x9e, 0xf5, 0x83, 0xac, 0x90, 0x37, 0x5b, 0xdf, 0x4d, 0x9b, 0x05, 0x6b, 0x5f, 0xaa, 0x87, 0x31, 0x87, 0x0e, 0x97, 0x90, 0xa0, 0xff, 0x12, 0x81, 0xcc, 0xfe, 0x66, 0xa3, 0x8e, 0x34, 0x33, 0x63, 0x27, 0x10, 0xa4, 0xf1, 0x57, 0x27, 0x72, 0x54, 0x45, 0x41, 0x62, 0xee, 0x00, 0x36, 0xaa, 0x1f, 0xfa, 0xa3, 0xb0, 0x27, 0xeb, 0x3e, 0xf3, 0xcf, 0x04, 0x17, 0x68, 0x22, 0xf1, 0x1e, 0x1c, 0x9e, 0x27, 0x7d, 0x82, 0xb3, 0x3f, 0x3c, 0x12, 0x63, 0x94, 0x3b, 0xae, 0x87, 0x3c, 0x33, 0x6a, 0x08, 0x63, 0x84, 0xc2, 0xf8, 0x87, 0xbd, 0xfd, 0x25, 0x92, 0xb7, 0x8d, 0xdb, 0xac, 0xe9, 0xcb, 0x3f, 0x04, 0x3d, 0xee, 0x9f, 0xf6, 0x17, 0xbe, 0xea, 0x41, 0x7f, 0x2b, 0x2d, 0x4a, 0xbf, 0x64, 0xea, 0x01, 0x83, 0xf2, 0x59, 0x82, 0x6c, 0xcb, 0x6c, 0x1f, 0x91, 0x53, 0xde, 0x8a, 0x36, 0x7f, 0x41, 0x7e, 0x19, 0x02, 0x80, 0x42, 0x8c, 0xd5, 0xc1, 0x3c, 0x22, 0x06, 0xf4, 0x2d, 0x09, 0x45, 0xbf, 0xc1, 0x12, 0xe3, 0xfc, 0xa3, 0xc2, 0x89, 0x11, 0x7f, 0x01, 0xcb, 0x49, 0xab, 0xc1, 0x50, 0x37, 0xca, 0x03, 0xb7, 0x44, 0x94, 0x16, 0xbf, 0xd6, 0xf5, 0xa6, 0xbc, 0x10, 0x86, 0xf2, 0x97, 0xea, 0x66, 0x15, 0xa3, 0x9f, 0x4d, 0xf0, 0xe6, 0xa5, 0xfb, 0x1f, 0x25, 0xd7, 0x71, 0xed, 0x85, 0x53, 0x5b, 0x86, 0x1c, 0x46, 0x29, 0xb5, 0xa8, 0xa8, 0x25, 0x27, 0x5a, 0x51, 0x27, 0x30, 0xa7, 0x94, 0x07, 0x21, 0xf7, 0x66, 0xe2, 0xab, 0x16, 0x0e, 0x59, 0xa2, 0x7a, 0x70, 0x30, 0xba, 0x6b, 0x9f, 0xf9, 0x4d, 0x22, 0x4e, 0xa3, 0x33, 0x7e, 0x49, 0x43, 0x62, 0x29, 0xf5, 0xc7, 0x61, 0x7e, 0x5f, 0xcd, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x53, 0x30, 0x51, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x93, 0xc8, 0x8f, 0xac, 0x37, 0x01, 0x7e, 0x4d, 0xd2, 0x87, 0x7a, 0xb5, 0x26, 0xba, 0xd1, 0xa6, 0x1a, 0xcd, 0xd1, 0xb2, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x93, 0xc8, 0x8f, 0xac, 0x37, 0x01, 0x7e, 0x4d, 0xd2, 0x87, 0x7a, 0xb5, 0x26, 0xba, 0xd1, 0xa6, 0x1a, 0xcd, 0xd1, 0xb2, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05, 0x30, 0x03, 0x01, 0x01, 0xff, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x01, 0x01, 0x00, 0x5b, 0x91, 0x51, 0xe1, 0x89, 0x20, 0xf5, 0xdf, 0x02, 0x94, 0x59, 0x76, 0x9e, 0xdc, 0x53, 0xf3, 0x17, 0x8f, 0x96, 0x17, 0xd1, 0x2f, 0x65, 0x36, 0xd4, 0x56, 0x7e, 0xd8, 0x0d, 0x7e, 0x59, 0x79, 0xab, 0x47, 0x67, 0x01, 0xb6, 0x9e, 0xf6, 0x7a, 0x0d, 0x20, 0xd2, 0xb2, 0x2d, 0x87, 0x84, 0x07, 0x40, 0x2d, 0x83, 0x1e, 0x16, 0x4f, 0x2d, 0x20, 0xaf, 0xf2, 0xca, 0xde, 0x10, 0x73, 0x41, 0xb9, 0x48, 0x3c, 0x4f, 0x9d, 0x55, 0xbc, 0xee, 0x68, 0xae, 0x66, 0x4d, 0x5d, 0x41, 0xa9, 0xbc, 0x51, 0x6d, 0xe2, 0x37, 0x0c, 0x0f, 0xf4, 0x43, 0xa0, 0x84, 0xf9, 0x40, 0xbc, 0x89, 0xaa, 0xcd, 0x14, 0xb4, 0xd5, 0xda, 0xd1, 0xb3, 0x2c, 0x4a, 0x56, 0x7e, 0x86, 0x2c, 0x71, 0xaa, 0x75, 0x86, 0x48, 0x14, 0x2a, 0xbc, 0x05, 0xab, 0x14, 0x72, 0x72, 0x01, 0xc8, 0xff, 0x02, 0x3d, 0x2e, 0xe9, 0xef, 0x21, 0x4d, 0x71, 0xf3, 0x0c, 0xba, 0x40, 0xfd, 0x9f, 0xb1, 0x40, 0xea, 0x47, 0x65, 0x3d, 0xb7, 0x52, 0xd8, 0xbb, 0x13, 0x30, 0x38, 0xb4, 0x3c, 0xbf, 0x76, 0x06, 0xe2, 0xb3, 0x3f, 0xf7, 0x7b, 0xdd, 0xdf, 0x54, 0x7b, 0x8d, 0x0c, 0x4d, 0x4a, 0x96, 0xcd, 0x14, 0x5c, 0x7d, 0xed, 0xb3, 0x2f, 0xbd, 0x27, 0xc8, 0x52, 0x6e, 0x58, 0x8e, 0x9c, 0x07, 0xa1, 0x52, 0xe2, 0x49, 0x8c, 0x04, 0x3f, 0x84, 0x32, 0x7b, 0xff, 0x5f, 0xf4, 0xf2, 0xdf, 0x3c, 0x73, 0xff, 0x9f, 0x63, 0x0e, 0xe5, 0x7f, 0xdf, 0xa8, 0x7e, 0x4d, 0xf3, 0x29, 0xd8, 0x2b, 0x41, 0x25, 0xbc, 0x73, 0x41, 0x3b, 0x1f, 0x39, 0x64, 0x48, 0x85, 0xe5, 0x66, 0x90, 0x8c, 0xd3, 0x8a, 0xce, 0xdc, 0xb5, 0x0d, 0x93, 0xb0, 0xd0, 0x8a, 0xef, 0x74, 0x8f, 0x28, 0x2f, 0x2c, 0x96, 0x4a, 0x4f, 0xc3, 0xf1, 0xde, 0x25, 0xff, 0xd4};
    struct altcp_tls_config *tls_config = altcp_tls_create_config_server_privkey_cert(key, sizeof(key), NULL, 0, cert, sizeof(cert));
    http_set_ssi_handler(mySSIHandler, ssitags, 2);
    httpd_inits(tls_config);
    while (true)
    {
        sleep_ms(500);
    }
}

Page 151 Simple HTTPS Bultin Server TLS and SSI CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background hardware_rtc pico_lwip_mbedtls pico_mbedtls pico_lwip_http)
pico_add_extra_outputs(main)

Page 151 Full listing not in book

Simple HTTPS Bultin Server LWIPOPTS.H TLS and SSI

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define LWIP_ALTCP               1
#define LWIP_ALTCP_TLS           1
#define LWIP_ALTCP_TLS_MBEDTLS   1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG  LWIP_DBG_ON
#define TCP_LISTEN_BACKLOG       1



#define HTTPD_ENABLE_HTTPS   1
#undef MEM_SIZE
#define MEM_SIZE                    8000
#define LWIP_HTTPD_SSI   1

#endif /* __LWIPOPTS_H__ */

Page 144 Full listing not in book

Simple HTTPS Bultin Server mbedtls_config.h TLS and SSI

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C

//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES
#define MBEDTLS_GCM_C

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client and server modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION
#define MBEDTLS_SSL_SRV_C

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"



Chapter 7

Page 157 Simple UDP server

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/udp.h"
#include "setupWifi.h"

int main()
{
    stdio_init_all();
    connect();

    struct udp_pcb *pcb = udp_new();
    udp_bind(pcb, IP_ADDR_ANY, 8080);

    ip_addr_t ip;
    IP4_ADDR(&ip, 192, 168, 11, 101);

    udp_connect(pcb, &ip, 8080);

    char message[] = "Hello UDP World";
    struct pbuf *p = pbuf_alloc(PBUF_TRANSPORT, strlen(message) + 1, PBUF_RAM);

    snprintf(p->payload, strlen(message) + 1, "%s", message);

    err_t er = udp_send(pcb, p);
    pbuf_free(p);
    while (true)
    {
        sleep_ms(500);
    }
}

Page 157 Full listing not in book

Simple UDP server lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define LWIP_DEBUG 1
#endif /* __LWIPOPTS_H__ */

Page 158 Full listing not in book

Simple UDP server Cmakelists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background)
pico_add_extra_outputs(main)

Page 158 Python UDP Client

import asyncio
class ClientDatagramProtocol(asyncio.DatagramProtocol):
    def datagram_received(self, data, addr):
        message = data.decode("utf8")
        print("Received",message,"from", addr)

async def main():
    loop = asyncio.get_running_loop()
    transport, protocol = await loop.create_datagram_endpoint(
          lambda: ClientDatagramProtocol(),
                    local_addr=('0.0.0.0', 8080))
    await asyncio.sleep(100000)
    transport.close()

asyncio.run(main())

Page 161 Full listing not in book

Simple UDP client

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/udp.h"
#include "setupWifi.h"

#define BUF_SIZE 1024

void recv(void *arg, struct udp_pcb *pcb, struct pbuf *p, const ip_addr_t *addr, u16_t port)
{
    char myBuff[BUF_SIZE];
    if (p != NULL)
    {
        printf("recv total %d  this buffer %d next %d \n", p->tot_len, p->len, p->next);
        printf("From %s:%d\n", ipaddr_ntoa(addr), port);
        pbuf_copy_partial(p, myBuff, p->tot_len, 0);
        myBuff[p->tot_len] = 0;
        printf("Buffer= %s\n", myBuff);
        pbuf_free(p);
    }
}

int main()
{
    stdio_init_all();
    connect();

    struct udp_pcb *pcb = udp_new();
    udp_recv(pcb, recv, NULL);

    udp_bind(pcb, IP_ADDR_ANY, 8080);

    //   ip_addr_t ip;
    //  IP4_ADDR(&ip, 192, 168, 11, 101);
    // IP4_ADDR(&ip, 192, 168, 11, 255);
    // udp_connect(pcb, &ip, 8080);

    while (true)
    {
        sleep_ms(500);
    }
}

Page 162 Python UDP Server

import asyncio

async def main():  
    loop = asyncio.get_running_loop()
    transport, protocol = await loop.create_datagram_endpoint(
                             lambda: asyncio.DatagramProtocol(),
                             local_addr=('0.0.0.0',8080))
    data=b"Hello UDP World"
    for i in range(20):
        transport.sendto(data,addr=("192.168.11.255",8080))
        await asyncio.sleep(1)
    transport.close()  
asyncio.run(main())

Chapter 8

Page 176 SNTP RTC main program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/pbuf.h"
#include "lwip/udp.h"
#include "setupWifi.h"
#include "hardware/rtc.h"
#include "time.h"
#include "lwip/dns.h"

bool getDateNow(struct tm *t)
{
    datetime_t rtc;
    bool state = rtc_get_datetime(&rtc);
    if (state)
    {

        t->tm_sec = rtc.sec;
        t->tm_min = rtc.min;
        t->tm_hour = rtc.hour;
        t->tm_mday = rtc.day;
        t->tm_mon = rtc.month - 1;
        t->tm_year = rtc.year - 1900;
        t->tm_wday = rtc.dotw;
        t->tm_yday = 0;
        t->tm_isdst = -1;
    }
    return state;
}

void setRTC(struct tm *datetime)
{
    datetime_t t;
    t.year = datetime->tm_year + 1900;
    t.month = datetime->tm_mon + 1;
    t.day = datetime->tm_mday;
    t.dotw = datetime->tm_wday;
    t.hour = datetime->tm_hour;
    t.min = datetime->tm_min;
    t.sec = datetime->tm_sec;
    rtc_init();
    rtc_set_datetime(&t);
}
struct timeStatus
{
    bool ready;
    struct udp_pcb *pcb;
};

void recv(void *arg, struct udp_pcb *pcb, struct pbuf *p, const ip_addr_t *addr, u16_t port)
{
    struct timeStatus *tstatus = (struct timeStatus *)arg;
    printf("SNTP responded\n");
    if (p != NULL)
    {
        uint8_t seconds_buf[4];
        pbuf_copy_partial(p, seconds_buf, sizeof(seconds_buf), 40);
        uint32_t seconds_since_1900 = seconds_buf[0] << 24 | seconds_buf[1] << 16 | seconds_buf[2] << 8 | seconds_buf[3];
        time_t seconds_since_1970 = seconds_since_1900 - 2208988800;
        struct tm *datetime = gmtime(&seconds_since_1970);
        setRTC(datetime);
        pbuf_free(p);
        udp_remove(pcb);
        tstatus->pcb=NULL;
        tstatus->ready = true;
    }
}

bool pollSNTP(struct timeStatus *tstatus)
{
    if (tstatus == NULL)
        return true;
    if (tstatus->ready)
    {
        free(tstatus);
        tstatus = NULL;
        return true;
    }
    return false;
}

void dns_found(const char *name, const ip_addr_t *ip, void *arg)
{
    struct timeStatus *tstatus = (struct timeStatus *)arg;
    printf("DNS %s\n", ipaddr_ntoa(ip));
    struct udp_pcb *pcb = udp_new();
    tstatus->pcb = pcb;
    udp_recv(pcb, recv, arg);
    udp_bind(pcb, IP_ADDR_ANY, 123);
    udp_connect(pcb, ip, 123);
    struct pbuf *p = pbuf_alloc(PBUF_TRANSPORT, 48, PBUF_RAM);
    uint8_t *payload = (uint8_t *)p->payload;
    memset(payload, 0, 48);
    *payload = 0x1b;
    err_t er = udp_send(pcb, p);
    pbuf_free(p);
}

struct timeStatus *getSNTP()
{
    struct timeStatus *tstatus = malloc(sizeof(struct timeStatus));
    tstatus->ready = false;
    tstatus->pcb=NULL;
    ip_addr_t ip;
    cyw43_arch_lwip_begin();
    err_t err = dns_gethostbyname("time.nist.gov", &ip, dns_found, tstatus);
    cyw43_arch_lwip_end();
    if (err == ERR_OK)
    {
        printf("DNS cache %s\n", ipaddr_ntoa(&ip));
        dns_found("", &ip, tstatus);
    }
    return tstatus;
}

void cancelSNTP(struct timeStatus *tstatus)
{
    if (tstatus != NULL)
    {
        udp_remove(tstatus->pcb);
        free(tstatus);
        tstatus = NULL;
        printf("canceled\n");
    }
}

int main()
{
    stdio_init_all();
    connect();

    while (true)
    {
        struct timeStatus *tstatus = getSNTP();
        sleep_ms(500);
        if (pollSNTP(tstatus))
            break;
        cancelSNTP(tstatus);
    }

    while (true)
    {
        struct tm t;
        getDateNow(&t);
        char Date[100];
        strftime(Date, sizeof(Date), "Date: %a, %d %b %Y %k:%M:%S %Z\r\n", &t);
        printf("%s\n", Date);
        sleep_ms(5000);
    }
}

Page 182 SNTP RTC App main program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "setupWifi.h"
#include "hardware/rtc.h"
#include <time.h>
#include "lwip/apps/sntp.h"

void SNTPSetRTC(u32_t t, u32_t us)
{
    printf("updating RTC\n");
    time_t seconds_since_1970 = t - 2208988800;
    struct tm *datetime = gmtime(&seconds_since_1970);
    datetime_t dt;
    dt.year = datetime->tm_year + 1900;
    dt.month = datetime->tm_mon + 1;
    dt.day = datetime->tm_mday;
    dt.dotw = datetime->tm_wday;
    dt.hour = datetime->tm_hour;
    dt.min = datetime->tm_min;
    dt.sec = datetime->tm_sec;
    rtc_init();
    rtc_set_datetime(&dt);
}

bool getDateNow(struct tm *t)
{
    datetime_t rtc;
    bool state = rtc_get_datetime(&rtc);
    if (state)
    {
        t->tm_sec = rtc.sec;
        t->tm_min = rtc.min;
        t->tm_hour = rtc.hour;
        t->tm_mday = rtc.day;
        t->tm_mon = rtc.month - 1;
        t->tm_year = rtc.year - 1900;
        t->tm_wday = rtc.dotw;
        t->tm_yday = 0;
        t->tm_isdst = -1;
    }
    return state;
}

int main()
{
    stdio_init_all();
    connect();

    sntp_setoperatingmode(SNTP_OPMODE_POLL);
    sntp_setservername(0, "pool.ntp.org");
    sntp_init();

    while (true)
    {
        struct tm t;
        if (getDateNow(&t))        {
            char Date[100];
            strftime(Date, sizeof(Date), "Date: %a, %d %b %Y %k:%M:%S %Z\r\n", &t);
            printf("%s\n", Date);
        }
        sleep_ms(5000);
    }
}

Page 183 Full listing not in book

SNTP RTC app lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H


// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS                      1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET                 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC             1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC             0
#endif
#define MEM_ALIGNMENT               4
#define MEM_SIZE                    4000
#define MEMP_NUM_TCP_SEG            32
#define MEMP_NUM_ARP_QUEUE          10
#define PBUF_POOL_SIZE              24
#define LWIP_ARP                    1
#define LWIP_ETHERNET               1
#define LWIP_ICMP                   1
#define LWIP_RAW                    1
#define TCP_WND                     (8 * TCP_MSS)
#define TCP_MSS                     1460
#define TCP_SND_BUF                 (8 * TCP_MSS)
#define TCP_SND_QUEUELEN            ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK  1
#define LWIP_NETIF_LINK_CALLBACK    1
#define LWIP_NETIF_HOSTNAME         1
#define LWIP_NETCONN                0
#define MEM_STATS                   0
#define SYS_STATS                   0
#define MEMP_STATS                  0
#define LINK_STATS                  0
// #define ETH_PAD_SIZE                2
#define LWIP_CHKSUM_ALGORITHM       3
#define LWIP_DHCP                   1
#define LWIP_IPV4                   1
#define LWIP_TCP                    1
#define LWIP_UDP                    1
#define LWIP_DNS                    1
#define LWIP_TCP_KEEPALIVE          1
#define LWIP_NETIF_TX_SINGLE_PBUF   1
#define DHCP_DOES_ARP_CHECK         0
#define LWIP_DHCP_DOES_ACD_CHECK    0

#ifndef NDEBUG
#define LWIP_DEBUG                  1
#define LWIP_STATS                  1
#define LWIP_STATS_DISPLAY          1
#endif

#define ETHARP_DEBUG                LWIP_DBG_OFF
#define NETIF_DEBUG                 LWIP_DBG_OFF
#define PBUF_DEBUG                  LWIP_DBG_OFF
#define API_LIB_DEBUG               LWIP_DBG_OFF
#define API_MSG_DEBUG               LWIP_DBG_OFF
#define SOCKETS_DEBUG               LWIP_DBG_OFF
#define ICMP_DEBUG                  LWIP_DBG_OFF
#define INET_DEBUG                  LWIP_DBG_OFF
#define IP_DEBUG                    LWIP_DBG_OFF
#define IP_REASS_DEBUG              LWIP_DBG_OFF
#define RAW_DEBUG                   LWIP_DBG_OFF
#define MEM_DEBUG                   LWIP_DBG_OFF
#define MEMP_DEBUG                  LWIP_DBG_OFF
#define SYS_DEBUG                   LWIP_DBG_OFF
#define TCP_DEBUG                   LWIP_DBG_OFF
#define TCP_INPUT_DEBUG             LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG            LWIP_DBG_OFF
#define TCP_RTO_DEBUG               LWIP_DBG_OFF
#define TCP_CWND_DEBUG              LWIP_DBG_OFF
#define TCP_WND_DEBUG               LWIP_DBG_OFF
#define TCP_FR_DEBUG                LWIP_DBG_OFF
#define TCP_QLEN_DEBUG              LWIP_DBG_OFF
#define TCP_RST_DEBUG               LWIP_DBG_OFF
#define UDP_DEBUG                   LWIP_DBG_OFF
#define TCPIP_DEBUG                 LWIP_DBG_OFF
#define PPP_DEBUG                   LWIP_DBG_OFF
#define SLIP_DEBUG                  LWIP_DBG_OFF
#define DHCP_DEBUG                  LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND  16384

#define SNTP_SERVER_DNS              1
#define SNTP_SUPPORT                 1
#define SNTP_UPDATE_DELAY       60*1000

#define SNTP_SET_SYSTEM_TIME_NTP(sec, us) \
 void SNTPSetRTC(u32_t, u32_t); \
  SNTPSetRTC(sec, us)

#define LWIP_DEBUG 1
#endif /* __LWIPOPTS_H__ */

Page 184 Full listing not in book

SNTP RTC app CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
 main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_sntp hardware_rtc)
pico_add_extra_outputs(main)

Chapter 9

Page 190 SMTP  main program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "setupWifi.h"

#include "lwip/apps/smtp.h"

void mailsent(void *arg, u8_t smtp_result, u16_t srv_err, err_t err)
{
    printf("mail (%p) sent with results: 0x%02x, 0x%04x, 0x%08x\n", arg,
           smtp_result, srv_err, err);
}

int main()
{
    stdio_init_all();
    connect();

    smtp_set_server_addr("iopress.info");
    smtp_set_server_port(25);  
    smtp_set_auth(NULL, NULL);
  smtp_send_mail("This email address is being protected from spambots. You need JavaScript enabled to view it.", "This email address is being protected from spambots. You need JavaScript enabled to view it.", "subject", "body", mailsent, NULL);
    while (true)
    {
        sleep_ms(10);
    }
}

Page 191 Full listing not in book

SMTP  CMakelists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
 main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_smtp)  
pico_add_extra_outputs(main)

Page 192 Full listing not in book

SMTP lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#define LWIP_DEBUG 1
#define SMTP_DEBUG LWIP_DBG_ON

#endif /* __LWIPOPTS_H__ */

Page 193 SMTPS main

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"

#include "setupWifi.h"
#include "lwip/altcp_tls.h"
#include "lwip/apps/smtp.h"

void mailsent(void *arg, u8_t smtp_result, u16_t srv_err, err_t err)
{
    printf("mail (%p) sent with results: 0x%02x, 0x%04x, 0x%08x\n", arg,
           smtp_result, srv_err, err);
}

int main()
{
    stdio_init_all();
    connect();
    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);
    smtp_set_tls_config(tls_config);

    smtp_set_server_addr("smtp.gmail.com");
    smtp_set_server_port(465);
    smtp_set_auth("gmailUSER", "App Password");

    smtp_send_mail("gmailUSER", "email address", "subject", "body", mailsent, NULL);
    while (true)
    {
        sleep_ms(10);
    }
}

Page 194 Full listing not in book

SMTPS mbedtls_config.h

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C

//EC KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_ECDHE_RSA_ENABLED
#define MBEDTLS_ECDH_C
#define MBEDTLS_ECDSA_C
#define MBEDTLS_ECP_C

/* Short Weierstrass curves (supporting ECP, ECDH, ECDSA) */
#define MBEDTLS_ECP_DP_SECP192R1_ENABLED
#define MBEDTLS_ECP_DP_SECP224R1_ENABLED
#define MBEDTLS_ECP_DP_SECP256R1_ENABLED
#define MBEDTLS_ECP_DP_SECP384R1_ENABLED
#define MBEDTLS_ECP_DP_SECP521R1_ENABLED
#define MBEDTLS_ECP_DP_SECP192K1_ENABLED
#define MBEDTLS_ECP_DP_SECP224K1_ENABLED
#define MBEDTLS_ECP_DP_SECP256K1_ENABLED
#define MBEDTLS_ECP_DP_BP256R1_ENABLED
#define MBEDTLS_ECP_DP_BP384R1_ENABLED
#define MBEDTLS_ECP_DP_BP512R1_ENABLED

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C

//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES
#define MBEDTLS_GCM_C

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//ECDHE-RSA-AES256-GCM-SHA384
//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 194 Full listing not in book

SMTPS lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND 16384
#undef MEM_SIZE
#define MEM_SIZE 8000

#define LWIP_ALTCP 1
#define LWIP_ALTCP_TLS 1
#define LWIP_ALTCP_TLS_MBEDTLS 1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG LWIP_DBG_ON
#define SMTP_DEBUG LWIP_DBG_ON

#endif /* __LWIPOPTS_H__ */

Page 194 Full listing not in book

SMTPS CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_mbedtls
pico_mbedtls pico_lwip_smtp)
pico_add_extra_outputs(main)



Chapter 10

Page 203 MQTT main program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/ip_addr.h"
#include "setupWifi.h"
#include "lwip/altcp.h"
#include "lwip/altcp_tls.h"
#include "lwip/apps/mqtt.h"

int mqttStatus = 0;

void mqtt_connection_cb(mqtt_client_t *client, void *arg, mqtt_connection_status_t status)
{
    if (status == MQTT_CONNECT_ACCEPTED)
    {
        mqttStatus = 1;
    }
}

static void pub_request_cb(void *arg, err_t result)
{
    printf("Publish result: %d\n", result);
    mqtt_client_t *client = (mqtt_client_t *)arg;
}

void sub_request_cb(void *arg, err_t result)
{
    printf("Subscribe result: %d\n", result);
    mqttStatus = 2;
}

static void incoming_publish_cb(void *arg, const char *topic, u32_t tot_len)
{
    printf("Topic %s. %d\n", topic, tot_len);
}

static void incoming_data_cb(void *arg, const u8_t *data, u16_t len, u8_t flags)
{
    char *payload = (char *)data;
    printf("payload\n%.*s\n", len, payload);
}

int main()
{
    stdio_init_all();
    connect();

    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);

    mqtt_client_t *client = mqtt_client_new();

    struct mqtt_connect_client_info_t ci;
    memset(&ci, 0, sizeof(ci));
    ci.client_id = "MyPicoW";
    ci.keep_alive = 10;

    ci.tls_config = tls_config;

    ip_addr_t ip;
    IP4_ADDR(&ip, 137, 135, 83, 217);
    // IP4_ADDR(&ip, 20, 79, 70, 109);

    err_t err = mqtt_client_connect(client, &ip, 8883, mqtt_connection_cb, 0, &ci);

    char payload[] = "Hello MQTT World";
    u8_t qos = 2;
    u8_t retain = 0;
    while (true)
    {
        switch (mqttStatus)
        {
        case 0:
            break;
        case 1:
            mqtt_set_inpub_callback(client, incoming_publish_cb, incoming_data_cb, NULL);
            err = mqtt_subscribe(client, "MyTopic", 1, sub_request_cb, NULL);
            break;

        case 2:
            err = mqtt_publish(client, "MyTopic", payload, strlen(payload), qos, retain, pub_request_cb, client);
            break;
        }
        sleep_ms(2000);
    }
}

Page 205 Full listing not in book

MQTT lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND 16384
#undef MEM_SIZE
#define MEM_SIZE 8000

#define LWIP_ALTCP 1
//#define LWIP_ALTCP_TLS 1
//#define LWIP_ALTCP_TLS_MBEDTLS 1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG LWIP_DBG_ON
#define MQTT_DEBUG LWIP_DBG_ON
#define MEMP_NUM_SYS_TIMEOUT (LWIP_NUM_SYS_TIMEOUT_INTERNAL + 1)
#define MQTT_REQ_MAX_IN_FLIGHT (5)

#endif /* __LWIPOPTS_H__ */

Page 205 Full listing not in book

MQTT Cmakelist.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_mqtt)
pico_add_extra_outputs(main)

Page 205 Full listing not in book

MQTT TLS  main program

#include <stdio.h>

#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/ip_addr.h"
#include "setupWifi.h"
#include "lwip/altcp.h"
#include "lwip/altcp_tls.h"
#include "lwip/apps/mqtt.h"

int mqttStatus = 0;

void mqtt_connection_cb(mqtt_client_t *client, void *arg, mqtt_connection_status_t status)
{
    if (status == MQTT_CONNECT_ACCEPTED)
    {
        mqttStatus = 1;
    }
}

static void pub_request_cb(void *arg, err_t result)
{
    printf("Publish result: %d\n", result);
    mqtt_client_t *client = (mqtt_client_t *)arg;
}

void sub_request_cb(void *arg, err_t result)
{
    printf("Subscribe result: %d\n", result);
    mqttStatus = 2;
}

static void incoming_publish_cb(void *arg, const char *topic, u32_t tot_len)
{
    printf("Topic %s. %d\n", topic, tot_len);
}

static void incoming_data_cb(void *arg, const u8_t *data, u16_t len, u8_t flags)
{
    char *payload = (char *)data;
    printf("payload\n%.*s\n", len, payload);
}

int main()
{
    stdio_init_all();
    connect();

    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);

    mqtt_client_t *client = mqtt_client_new();

    struct mqtt_connect_client_info_t ci;
    memset(&ci, 0, sizeof(ci));
    ci.client_id = "MyPicoW";
    ci.keep_alive = 10;

    ci.tls_config = tls_config;

    ip_addr_t ip;
    IP4_ADDR(&ip, 137, 135, 83, 217);
    // IP4_ADDR(&ip, 20, 79, 70, 109);

    err_t err = mqtt_client_connect(client, &ip, 8883, mqtt_connection_cb, 0, &ci);

    char payload[] = "Hello MQTT World";
    u8_t qos = 2;
    u8_t retain = 0;
    while (true)
    {
        switch (mqttStatus)
        {
        case 0:
            break;
        case 1:
            mqtt_set_inpub_callback(client, incoming_publish_cb, incoming_data_cb, NULL);
            err = mqtt_subscribe(client, "MyTopic", 1, sub_request_cb, NULL);
            break;

        case 2:
            err = mqtt_publish(client, "MyTopic", payload, strlen(payload), qos, retain, pub_request_cb, client);
            break;
        }
        sleep_ms(2000);
    }
}

Page 205 Full listing not in book

MQTT TLS lwipopts.h

#ifndef _LWIPOPTS_EXAMPLE_COMMONH_H
#define _LWIPOPTS_EXAMPLE_COMMONH_H

// Common settings used in most of the pico_w examples
// (see https://www.nongnu.org/lwip/2_1_x/group__lwip__opts.html for details)

// allow override in some examples
#ifndef NO_SYS
#define NO_SYS 1
#endif
// allow override in some examples
#ifndef LWIP_SOCKET
#define LWIP_SOCKET 0
#endif
#if PICO_CYW43_ARCH_POLL
#define MEM_LIBC_MALLOC 1
#else
// MEM_LIBC_MALLOC is incompatible with non polling versions
#define MEM_LIBC_MALLOC 0
#endif
#define MEM_ALIGNMENT 4
#define MEM_SIZE 4000
#define MEMP_NUM_TCP_SEG 32
#define MEMP_NUM_ARP_QUEUE 10
#define PBUF_POOL_SIZE 24
#define LWIP_ARP 1
#define LWIP_ETHERNET 1
#define LWIP_ICMP 1
#define LWIP_RAW 1
#define TCP_WND (8 * TCP_MSS)
#define TCP_MSS 1460
#define TCP_SND_BUF (8 * TCP_MSS)
#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1)) / (TCP_MSS))
#define LWIP_NETIF_STATUS_CALLBACK 1
#define LWIP_NETIF_LINK_CALLBACK 1
#define LWIP_NETIF_HOSTNAME 1
#define LWIP_NETCONN 0
#define MEM_STATS 0
#define SYS_STATS 0
#define MEMP_STATS 0
#define LINK_STATS 0
// #define ETH_PAD_SIZE 2
#define LWIP_CHKSUM_ALGORITHM 3
#define LWIP_DHCP 1
#define LWIP_IPV4 1
#define LWIP_TCP 1
#define LWIP_UDP 1
#define LWIP_DNS 1
#define LWIP_TCP_KEEPALIVE 1
#define LWIP_NETIF_TX_SINGLE_PBUF 1
#define DHCP_DOES_ARP_CHECK 0
#define LWIP_DHCP_DOES_ACD_CHECK 0

#ifndef NDEBUG
#define LWIP_DEBUG 1
#define LWIP_STATS 1
#define LWIP_STATS_DISPLAY 1
#endif

#define ETHARP_DEBUG LWIP_DBG_OFF
#define NETIF_DEBUG LWIP_DBG_OFF
#define PBUF_DEBUG LWIP_DBG_OFF
#define API_LIB_DEBUG LWIP_DBG_OFF
#define API_MSG_DEBUG LWIP_DBG_OFF
#define SOCKETS_DEBUG LWIP_DBG_OFF
#define ICMP_DEBUG LWIP_DBG_OFF
#define INET_DEBUG LWIP_DBG_OFF
#define IP_DEBUG LWIP_DBG_OFF
#define IP_REASS_DEBUG LWIP_DBG_OFF
#define RAW_DEBUG LWIP_DBG_OFF
#define MEM_DEBUG LWIP_DBG_OFF
#define MEMP_DEBUG LWIP_DBG_OFF
#define SYS_DEBUG LWIP_DBG_OFF
#define TCP_DEBUG LWIP_DBG_OFF
#define TCP_INPUT_DEBUG LWIP_DBG_OFF
#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF
#define TCP_RTO_DEBUG LWIP_DBG_OFF
#define TCP_CWND_DEBUG LWIP_DBG_OFF
#define TCP_WND_DEBUG LWIP_DBG_OFF
#define TCP_FR_DEBUG LWIP_DBG_OFF
#define TCP_QLEN_DEBUG LWIP_DBG_OFF
#define TCP_RST_DEBUG LWIP_DBG_OFF
#define UDP_DEBUG LWIP_DBG_OFF
#define TCPIP_DEBUG LWIP_DBG_OFF
#define PPP_DEBUG LWIP_DBG_OFF
#define SLIP_DEBUG LWIP_DBG_OFF
#define DHCP_DEBUG LWIP_DBG_OFF

#undef TCP_WND
#define TCP_WND 16384
#undef MEM_SIZE
#define MEM_SIZE 8000

#define LWIP_ALTCP 1
#define LWIP_ALTCP_TLS 1
#define LWIP_ALTCP_TLS_MBEDTLS 1

#define LWIP_DEBUG 1
#define ALTCP_MBEDTLS_DEBUG LWIP_DBG_ON
#define MQTT_DEBUG LWIP_DBG_ON
#define MEMP_NUM_SYS_TIMEOUT (LWIP_NUM_SYS_TIMEOUT_INTERNAL + 1)
#define MQTT_REQ_MAX_IN_FLIGHT (5)

#endif /* __LWIPOPTS_H__ */

Page 205 Full listing not in book

MQTT TLS mbedtls_config.h

//Hardware config
#define MBEDTLS_NO_PLATFORM_ENTROPY
#define MBEDTLS_ENTROPY_HARDWARE_ALT
#define MBEDTLS_HAVE_TIME

//error reporting
#define MBEDTLS_ERROR_C
//used by LwIP
#define MBEDTLS_ENTROPY_C
#define MBEDTLS_CTR_DRBG_C

//EC KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_ECDHE_RSA_ENABLED
#define MBEDTLS_ECDH_C
#define MBEDTLS_ECDSA_C
#define MBEDTLS_ECP_C

/* Short Weierstrass curves (supporting ECP, ECDH, ECDSA) */
#define MBEDTLS_ECP_DP_SECP192R1_ENABLED
#define MBEDTLS_ECP_DP_SECP224R1_ENABLED
#define MBEDTLS_ECP_DP_SECP256R1_ENABLED
#define MBEDTLS_ECP_DP_SECP384R1_ENABLED
#define MBEDTLS_ECP_DP_SECP521R1_ENABLED
#define MBEDTLS_ECP_DP_SECP192K1_ENABLED
#define MBEDTLS_ECP_DP_SECP224K1_ENABLED
#define MBEDTLS_ECP_DP_SECP256K1_ENABLED
#define MBEDTLS_ECP_DP_BP256R1_ENABLED
#define MBEDTLS_ECP_DP_BP384R1_ENABLED
#define MBEDTLS_ECP_DP_BP512R1_ENABLED

//RSA KEY EXCHANGE
#define MBEDTLS_KEY_EXCHANGE_RSA_ENABLED
#define MBEDTLS_RSA_C

//general key exchange
#define MBEDTLS_PKCS1_V15
#define MBEDTLS_BIGNUM_C
#define MBEDTLS_PK_C
#define MBEDTLS_PK_PARSE_C

//encryption
#define MBEDTLS_AES_C
#define MBEDTLS_CCM_C
#define MBEDTLS_CIPHER_MODE_CBC
#define MBEDTLS_AES_FEWER_TABLES
#define MBEDTLS_GCM_C

//certs
#define MBEDTLS_X509_CRT_PARSE_C
#define MBEDTLS_X509_USE_C
#define MBEDTLS_OID_C
#define MBEDTLS_ASN1_PARSE_C
#define MBEDTLS_ASN1_WRITE_C

//hash methods
#define MBEDTLS_SHA1_C
#define MBEDTLS_SHA224_C
#define MBEDTLS_SHA256_C
#define MBEDTLS_SHA512_C

//ECDHE-RSA-AES256-GCM-SHA384
//TLS
#define MBEDTLS_CIPHER_C
#define MBEDTLS_SSL_TLS_C
#define MBEDTLS_MD_C

//enable client modes and TLS
#define MBEDTLS_SSL_CLI_C
#define MBEDTLS_SSL_SERVER_NAME_INDICATION

//enable TLS 1.2
#define MBEDTLS_SSL_PROTO_TLS1_2

#include "/home/pi/pico/pico-sdk/lib/mbedtls/include/mbedtls/check_config.h"

Page 205 Full listing not in book

MQTT TLS CMakeLists.txt

cmake_minimum_required(VERSION 3.13)
set(PICO_BOARD pico_w)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)

include(pico_sdk_import.cmake)
project(PicoW C CXX ASM)
pico_sdk_init()

add_executable(main
main.c
)

target_include_directories(main PRIVATE ${CMAKE_CURRENT_LIST_DIR})

target_link_libraries(main pico_stdlib pico_cyw43_arch_lwip_threadsafe_background pico_lwip_mqtt pico_lwip_mbedtls
pico_mbedtls)
pico_add_extra_outputs(main)

Page 207  MQTT HiveMQ main program Note works with modified mqtt.h and mqtt.c

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/cyw43_arch.h"
#include "lwip/ip_addr.h"
#include "setupWifi.h"
#include "lwip/altcp.h"
#include "lwip/altcp_tls.h"
#include "lwip/apps/mqtt.h"

int mqttStatus = 0;

void mqtt_connection_cb(mqtt_client_t *client, void *arg, mqtt_connection_status_t status)
{
    if (status == MQTT_CONNECT_ACCEPTED)
    {
        mqttStatus = 1;
    }
}

static void pub_request_cb(void *arg, err_t result)
{
    printf("Publish result: %d\n", result);
    mqtt_client_t *client = (mqtt_client_t *)arg;
}

void sub_request_cb(void *arg, err_t result)
{
    printf("Subscribe result: %d\n", result);
    mqttStatus = 2;
}

static void incoming_publish_cb(void *arg, const char *topic, u32_t tot_len)
{
    printf("Topic %s. %d\n", topic, tot_len);
}

static void incoming_data_cb(void *arg, const u8_t *data, u16_t len, u8_t flags)
{
    char *payload = (char *)data;
    printf("payload\n%.*s\n", len, payload);
}

int main()
{
    stdio_init_all();
    connect();

    struct altcp_tls_config *tls_config = altcp_tls_create_config_client(NULL, 0);
    mqtt_client_t *client = mqtt_client_new();

    struct mqtt_connect_client_info_t ci;
    memset(&ci, 0, sizeof(ci));
    ci.client_id = "MyPicoW";
    ci.client_user = "username";
    ci.client_pass = "password";
    ci.keep_alive = 10;
    ci.tls_config = tls_config;
    strncpy(ci.domName, "1a6d2dccd35744888e4b7c6f8e65f613.s2.eu.hivemq.cloud", 100);
    ip_addr_t ip;
    // IP4_ADDR(&ip, 137, 135, 83, 217);
    IP4_ADDR(&ip, 20, 79, 70, 109);

    err_t err = mqtt_client_connect(client, &ip, 8883, mqtt_connection_cb, 0, &ci);

    char payload[] = "Hello MQTT World";
    u8_t qos = 2;
    u8_t retain = 0;
    while (true)
    {
        switch (mqttStatus)
        {
        case 0:
            break;
        case 1:
            mqtt_set_inpub_callback(client, incoming_publish_cb, incoming_data_cb, NULL);
            err = mqtt_subscribe(client, "MyTopic", 1, sub_request_cb, NULL);
            break;

        case 2:
            err = mqtt_publish(client, "MyTopic", payload, strlen(payload), qos, retain, pub_request_cb, client);
            break;
        }
        sleep_ms(2000);
    }
}

Programming the Raspberry Pi Pico in MicroPython

picoPython360

 

We have decided not to make the programs available as a download because this is not the point of the book - the programs are not finished production code but something you should type in and study.

The best solution is to provide the source code of the programs in a form that can be copied and pasted into Thonny or VS Code project. 

The only downside is that you have to create a project to paste the code into.

To do this follow the instructions in the book.

All of the programs below were copy and pasted from working programs in the IDE. They have been formatted using the built in formatter and hence are not identical in layout to the programs in the book. This is to make copy and pasting them easier. The programs in the book are formatted to be easy to read on the page.

If anything you consider important is missing or if you have any requests or comments  contact:

This email address is being protected from spambots. You need JavaScript enabled to view it. 

Page 30

from machine import Pin
import time

pin = Pin(25, Pin.OUT)

while True:
    pin.value(1)
    time.sleep(1)
    pin.value(0)
    time.sleep(1)

Page 30

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.toggle()
    time.sleep(1)

Page 34

from machine import  Pin
pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    pin.value(0)

Page 34

from machine import  Pin
def flash():
    pin = Pin(22, Pin.OUT)
    while True:
        pin.value(1)
        pin.value(0)
flash()

Page 35

from machine import Pin


@micropython.native
def flash():
    pin = Pin(22, Pin.OUT)
    while True:
        pin.value(1)
        pin.value(0)
 
flash()

Page 36

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    time.sleep(0.5)
    pin.value(0)
    time.sleep(0.5)

Page 36

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    time.sleep_us(10)
    pin.value(0)
    time.sleep_us(10)

Page 32

from machine import Pin
import time
pin = Pin(22, Pin.OUT)
n = 10
while True:
    for i in range(n):
        pass
    pin.value(1)
    for i in range(n):
        pass
    pin.value(0)

Page 38

from machine import Pin

pin1 = Pin(21, Pin.OUT)
pin2 = Pin(22, Pin.OUT)
while True:
    pin1.value(1)
    pin2.value(0)
    pin1.value(0)
    pin2.value(1)

Page 41

from machine import Pin
import machine

def gpio_get():
    return machine.mem32[0xd0000000+0x010]

def gpio_set(value, mask):
    machine.mem32[0xd0000000 +  0x01C] = (machine.mem32[0xd0000000+0x010]) ^ value & mask


pin = Pin(22, Pin.OUT)
pin = Pin(21, Pin.OUT)
value1 = 1 << 22 | 0 << 21
value2 = 0 << 22 | 1 << 21
mask = 1 << 22 | 1 << 21
while True:
    gpio_set(value1, mask)
    gpio_set(value2, mask)

Page 61

from machine import Pin
import time
pinIn = Pin(22, Pin.IN, Pin.PULL_DOWN)
pinLED = Pin(25, Pin.OUT)

while True:
    if pinIn.value():
        pinLED.on()
    else:
        pinLED.off()
    time.sleep(0.5)

Page 62

from machine import Pin
import time
pinIn = Pin(22, Pin.IN, Pin.PULL_DOWN)
pinLED = Pin(25, Pin.OUT)

while True:
    while pinIn.value() == 0:
        pass
    while pinIn.value() == 1:
        pass
    pinLED.on()
    time.sleep(1)
    pinLED.off()

Page 63

 
from machine import Pin
import time
pinIn = Pin(22, Pin.IN, Pin.PULL_DOWN)
pinLED = Pin(25, Pin.OUT)

while True:
    while pinIn.value() == 0:
        pass
    t = time.ticks_ms()
    time.sleep_ms(1)
    while pinIn.value() == 1:
        pass
    t = time.ticks_diff(time.ticks_ms(), t)
    if t < 2000:
        pinLED.on()
        time.sleep(1)
        pinLED.off()
    else:
        for i in range(10):
            pinLED.on()
            time.sleep_ms(100)
            pinLED.off()
            time.sleep_ms(100)

Page 64

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

while True:
    while pinIn.value() == 1:
        pass
    while pinIn.value() == 0:
        pass

    t = time.ticks_us()
    while pinIn.value() == 1:
        pass
    t = time.ticks_diff(time.ticks_us(), t)
    print(t)
    time.sleep(1)

Page 65

import time
import machine

pinIn = machine.Pin(22, machine.Pin.IN)

while True:
    t = machine.time_pulse_us(pinIn, 1)
    print(t)
    time.sleep(1)

Page 65

import machine
import time

import machine
pinIn = machine.Pin(22, machine.Pin.IN)

while True:
    while pinIn.value() == 1:
        pass
    t = machine.time_pulse_us(pinIn, 1)
    print(t)
    time.sleep(1)

Page 68

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

s = 0
count = 0
while True:
    i = pinIn.value()
    t = time.ticks_add(time.ticks_us(), 1000*100)
    if s == 0:  # button not pushed
        if i:
            s = 1
            count = count+1
            print("Button Push ", count)
    elif s == 1:  # button pushed
        if not i:
            s = 0
    else:
        s = 0
    while time.ticks_us() < t:
        pass

Page 70

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

s = 0
while True:
    i = pinIn.value()
    t = time.ticks_add(time.ticks_us(), 1000*100)
    if s == 0:  # button not pushed
        if i:
            s = 1
        tpush = t
    elif s == 1:  # button pushed
        if not i:
            s = 0
            if time.ticks_diff(t, tpush) > 2000000:
                print("Button held \n\r")
            else:
                print("Button pushed \n\r")
    else:
        s = 0
    while time.ticks_us() < t:
        pass

Page 71  Corrected - see Erata.

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)
pinLED1 = Pin(21, Pin.OUT)
pinLED2 = Pin(20, Pin.OUT)
pinLED3 = Pin(19, Pin.OUT)
pinLED1.on()
pinLED2.off()
pinLED3.off()
s=0
buttonState=pinIn.value()
while True:
    buttonNow=pinIn.value()
    edge=buttonState-buttonNow
    buttonState=buttonNow
    t=time.ticks_add(time.ticks_us(),1000*100)
    if s==0:
        if edge==1:
            s=1
            pinLED1.off()
            pinLED2.on()
            pinLED3.off()
    
    elif s==1:
        if edge==1:
            s=2
            pinLED1.off()
            pinLED2.off()
            pinLED3.on()
    elif s==2:
        if edge==1:
            s=0
            pinLED1.on()
            pinLED2.off()
            pinLED3.off()
    else:
        s=0
    while time.ticks_us()<t:
        pass

Page 79

from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_UP)
while True:
    event = gpio_get_events(22)
    if(event & Pin.IRQ_FALLING):
        print("falling")
    if(event & Pin.IRQ_RISING):
        print("rising")
    gpio_clear_events(22, Pin.IRQ_FALLING | Pin.IRQ_RISING)
    sleep(0.5)

Page 79

from utime import sleep
from machine import Pin

pin = Pin(22, Pin.IN, Pin.PULL_DOWN)

print("Press Button")
sleep(10)
if pin.value():
    print("Button Pressed")
else:
    print("Button Not Pressed")

Page 80

from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)

print("Press Button")
gpio_clear_events(22, Pin.IRQ_FALLING)
sleep(10)
event = gpio_get_events(22)
gpio_clear_events(22, Pin.IRQ_FALLING)
if event & Pin.IRQ_FALLING:
    print("Button Pressed")
else:
    print("Button Not Pressed")

Page 81

import time
from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
while True:
    gpio_clear_events(22, Pin.IRQ_FALLING | Pin.IRQ_RISING)
    while not(gpio_get_events(22) & Pin.IRQ_RISING):
        pass
    t = time.ticks_us()
    while not(gpio_get_events(22) & Pin.IRQ_FALLING):
        pass
    t = time.ticks_diff(time.ticks_us(), t)
    print(t)
    sleep(1)

Page 84

import time
from machine import Pin
import machine
import array

count = 0
t = array.array('L', [0]*20)


def myHandler(pin):
    global t, count
    t[count] = time.ticks_us()
    count = count+1
    if count > 19:
        for i in range(1, 20):
            print(time.ticks_diff(t[i], t[i-1]))
        pin.irq(None, Pin.IRQ_RISING, hard=True)
        return


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
pin.irq(myHandler, Pin.IRQ_RISING, hard=False)

Page 86

import time
from machine import Pin


def myHandler(pin):
    print(time.ticks_us())


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
pin.irq(myHandler, Pin.IRQ_RISING, hard=True)
while True:
    print("doing something useful")

Page 92

from machine import Pin, PWM
pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))

pwm16.freq(250)

pwm16.duty_u16(65535//2)
pwm17.duty_u16(65535//4)

Page 93

from machine import Pin, PWM
import machine


def pwm_set_phase(sliceNo, phase):
    Addr = 0x40050000 + 0x14*sliceNo
    if phase:
        machine.mem32[Addr] = machine.mem32[Addr] | 0x2
    else:
        machine.mem32[Addr] = machine.mem32[Addr] & 0xFFFFFFFD


pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))
pwm16.freq(250)
pwm_set_phase(0, True)
pwm16.duty_u16(65535//2)
pwm17.duty_u16(65535//4)

Page 94

from machine import Pin, PWM
import machine


def pwm_set_polarity(sliceNo, channel, invert):
    Addr = 0x40050000 + 0x14*sliceNo
    if invert:
        machine.mem32[Addr] = machine.mem32[Addr] | 0x1 << (2+channel)
    else:
        machine.mem32[Addr] = machine.mem32[Addr] & ~(0x1 << (2+channel))


pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))

pwm16.freq(250)
pwm_set_polarity(0, 1, True)
pwm16.duty_u16(65535//4)
pwm17.duty_u16(65535//4)

Page 95

from machine import Pin, PWM

pwm16 = PWM(Pin(16))

pwm16.freq(50)

pwm16.duty_u16(65535//2)
while True:
    pwm16.duty_u16(65535//2)
    pwm16.duty_u16(65535//4)

Page 98

from machine import Pin, PWM
import array
import machine
import math


def pwm_get_wrap(sliceNo):
    Addr = 0x40050000 + 0x10+0x14*sliceNo
    return (machine.mem32[Addr])


wave = array.array('H', [0]*256)
for i in range(256):
    wave[i] = int(65535//2 + (math.sin(i * 2.0 * 3.14159 / 256.0) * 65535//2))


pwm16 = PWM(Pin(16))
pwm16.freq(125000000//256)

print(pwm_get_wrap(0))
while(True):
    for i in range(256):
        pwm16.duty_u16(wave[i])

Page 28

from utime import sleep_ms
from machine import Pin, PWM

pwm25 = PWM(Pin(25))
pwm25.freq(2000)

while True:
    for d in range(0,65535,655):
        pwm25.duty_u16(d)
        sleep_ms(50)

Page 101

from utime import sleep_ms
from machine import Pin, PWM

pwm25 = PWM(Pin(25))
pwm25.freq(2000)

while True:
    for b in range(0,100):
        pwm25.duty_u16(int(65535*b*b*b/1000000))
        sleep_ms(50)

Page 111

from machine import Pin, PWM
from time import sleep

class Motor:
    def __init__(self, pinNo):
        self.gpio = pinNo
        self._on = False
        self.speed=0

        self.pwm1=PWM(Pin(pinNo))
        self.pwm1.freq(2000)
        self.pwm1.duty_u16(0)

    def setSpeed(self,s):
        self._on=True
        self.speed=s
        self.pwm1.duty_u16(int(65535*s/100))
    
    def off(self):
        self._on=False
        self.pwm1.duty_u16(0)
    
    def on(self):
        self._on=True
        self.pwm1.duty_u16(int(65535*self.speed/100))

motor=Motor(16)
motor.setSpeed(50)
sleep(1)
motor.off()
sleep(1)
motor.setSpeed(90)
sleep(1)
motor.off()

Page 116

from machine import Pin, PWM
from time import sleep

class Motor:
    def __init__(self, pinNo):
        self.gpio = pinNo
        self._on = False
        self.speed=0

        self.pwm1=PWM(Pin(pinNo))
        self.pwm1.freq(2000)
        self.pwm1.duty_u16(0)

    def setSpeed(self,s):
        self._on=True
        self.speed=s
        self.pwm1.duty_u16(int(65535*s/100))
    
    def off(self):
        self._on=False
        self.pwm1.duty_u16(0)
    
    def on(self):
        self._on=True
        self.pwm1.duty_u16(int(65535*self.speed/100))

class BiMotor(Motor):
    def __init__(self, pinNo):
        super().__init__(pinNo)
        self.forward=True
        self.pwm2=PWM(Pin(pinNo+1))
        self.pwm2.duty_u16(0)
    
    def setForward(self,forward):
        if self.forward==forward:
            return
        self.pwm1.duty_u16(0)
        self.pwm1,self.pwm2=self.pwm2,self.pwm1        
        self.forward=forward
        self.pwm1.duty_u16(int(65535*self.speed/100))

motor=BiMotor(16)
motor.setSpeed(50)
sleep(1)
motor.setForward(False)
sleep(1)
motor.setSpeed(90)
sleep(1)
motor.setForward(True)
motor.off()

Page 115

from machine import Pin, PWM
from time import sleep

class Servo:
    def __init__(self, pinNo):
        self.pwm = PWM(Pin(pinNo))
        self.pwm.freq(50)
        self.position = 65535*2.5/100

    def setPosition(self, p):
        self.position = p
        self.pwm.duty_u16(int(65535*p/1000 + 65535*2.5/100))

servo=Servo(16)
servo.setPosition(100.0)
sleep(1)
servo.setPosition(50.0)
sleep(1)
servo.setPosition(0)

Page 120

from machine import Pin, PWM
import machine
from time import sleep


class Servo:
    def __init__(self, pinNo):
        self.pwm = PWM(Pin(pinNo))
        self.pin = pinNo
        self.pwm.freq(50)
        self.position = 65535*2.5/100

    def setPosition(self, p):
        self.position = p
        self.pwm.duty_u16(int(65535*p/1000 + 65535*2.5/100))

    def getSlice(self):
        return (self.pin >> 1) & 0x07

    def getChannel(self):
        return self.pin & 1

    def setPolarity(self, invert):
        sliceNo = self.getSlice()
        channel = self.getChannel()
        Addr = 0x40050000 + 0x14*sliceNo
        if invert:
            machine.mem32[Addr] = machine.mem32[Addr] | 0x1 << (2+channel)
        else:
            machine.mem32[Addr] = machine.mem32[Addr] & ~(0x1 << (2+channel))


servo = Servo(16)
servo.setPolarity(True)
servo.setPosition(100.0)
sleep(1)
servo.setPosition(50.0)
sleep(1)
servo.setPosition(0)

Page 134

from utime import sleep_ms
from machine import Pin
import machine


class StepperBi4():
    def __init__(self, pinA):
        self.phase = 0
        self.pinA = pinA
        self.timer = None
        self.forward = True
        self.speed = 0

        self.gpios = tuple([Pin(pinA, Pin.OUT), Pin(
            pinA+1, Pin.OUT), Pin(pinA+2, Pin.OUT), Pin(pinA+3, Pin.OUT)])
        self.gpios[0].high()
        self.gpioMask = 0xF << self.pinA
        self.halfstepSeq = [0x1, 0x3, 0x2, 0x6, 0x4, 0xC, 0x8, 0x9]
#   [
#             [0,0,0,1],
#             [0,0,1,1],
#             [0,0,1,0],
#             [0,1,1,0],
#             [0,1,0,0],
#             [1,1,0,0],
#             [1,0,0,0],
#             [1,0,0,1]
#    ]

    def _gpio_set(self, value, mask):
        machine.mem32[0xd0000000 +
                      0x01C] = (machine.mem32[0xd0000000+0x010] ^ value) & mask

    def setPhase(self, phase):
        value = self.halfstepSeq[phase] << self.pinA
        self._gpio_set(value, self.gpioMask)
        self.phase = phase

    def stepForward(self):
        self.phase = (self.phase+1) % 8
        self.setPhase(self.phase)

    def stepReverse(self):
        self.phase = (self.phase-1) % 8
        self.setPhase(self.phase)

    def doRotate(self, timer):
        if self.forward:
            self.stepForward()
        else:
            self.stepReverse()

    def rotate(self, forward, speed):
        self.forward = forward
        self.speed = speed
        if speed == 0:
            self.timer.deinit()
            self.timer = None
            return
        if self.timer == None:
            self.timer = machine.Timer()
        self.timer.init(freq=speed, mode=machine.Timer.PERIODIC,
                        callback=self.doRotate)


step = StepperBi4(16)
step.setPhase(0)
while True:
    step.rotate(True, 100)
    sleep_ms(500)
    step.rotate(True, 0)
    sleep_ms(500)

Page 144

from machine import Pin, SPI

spi = SPI(0, sck=Pin(6), miso=Pin(4), mosi=Pin(7))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)

read = bytearray(3)
write = bytearray([0xAA, 0xAA, 0xAA])
spi.write_readinto(write, read)

print(read, write)
spi.deinit()

Page 150

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep

spi = SPI(0, sck=Pin(18), miso=Pin(16), mosi=Pin(19))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)

CS = Pin(17, Pin.OUT)
CS.high()
sleep_ms(1)

write = bytearray([0xD0])
CS.low()
spi.write(write)
read = spi.read(1)
CS.high()
print("Chip ID is", hex(read[0]))

CS.low()
write = bytearray([0xF2, 0x01])
spi.write(write)
write = bytearray([0xF4, 0x27])
spi.write(write)
CS.high()

CS.low()
write = bytearray([0xF7])
spi.write(write)
sleep_ms(10)
rBuff = spi.read(8)
CS.high()

pressure = (rBuff[0] << 12) | (rBuff[1] << 4) | (rBuff[2] >> 4)
temperature = (rBuff[3] << 12) | (rBuff[4] << 4) | (rBuff[5] >> 4)
humidity = rBuff[6] << 8 | rBuff[7]

print("Humidity = ", humidity)
print("Pressure = ", pressure)
print("Temp. = ", temperature)

Page 155

import machine
import utime
sensor_temp = machine.ADC(4)
conversion_factor = 3.3 / (65535)

while True:
    reading = sensor_temp.read_u16() * conversion_factor
    temperature = 27 - (reading - 0.706)/0.001721
    print(temperature)
    utime.sleep(2)

Page 161

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep

spi = SPI(0, sck=Pin(18), miso=Pin(16), mosi=Pin(19))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)
CS = Pin(17, Pin.OUT)
CS.high()
sleep_ms(1)
CS.low()
write = bytearray([0x01, 0x80, 0x00])
read = bytearray(3)
spi.write_readinto(write, read)
CS.high()
data = (read[1] & 0x03) << 8 | read[2]
volts = data * 3.3 / 1023.0
print(volts)
spi.deinit()

Page 162

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep


class spiADC:
    def __init__(self, spi, sckNo, misoNo, mosiNo, CSNo):
        self.spi = SPI(spi, sck=Pin(sckNo), miso=Pin(misoNo), mosi=Pin(mosiNo))
        self.spi.init(baudrate=500_000, bits=8, polarity=0,
                      phase=0, firstbit=SPI.MSB)
        self.CS = Pin(CSNo, Pin.OUT)
        self.CS.high()
        sleep_ms(1)

    def read(self, chan):
        write = bytearray([0x01, (0x08 | chan) << 4, 0x00])
        self.CS.low()
        read = bytearray(3)
        self.spi.write_readinto(write, read)
        self.CS.high()
        data = (read[1] & 0x03) << 8 | read[2]
        volts = data * 3.3 / 1023.0
        return volts


adc = spiADC(0, 18, 16, 19, 17)
volts = adc.read(1)
print(volts)

Page 176

from machine import Pin,I2C

i2c0=I2C(0,scl=Pin(17),sda=Pin(16),freq=400000)

buf = bytearray([0xE7])
i2c0.writeto( 0x40, buf, True)
read= i2c0.readfrom(0x40, 1, True)
print("User Register =",read)

Page 178

from utime import sleep_ms
from machine import Pin, I2C
from time import sleep

i2c0 = I2C(0, scl=Pin(17), sda=Pin(16), freq=100*1000)

buf = bytearray([0xE3])
i2c0.writeto(0x40, buf, False)
read = i2c0.readfrom(0x40, 3, True)
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)

Page 182

from utime import sleep_ms
from machine import Pin, I2C
from time import sleep


def crcCheck(msb, lsb, check):
    data32 = (msb << 16) | (lsb << 8) | check
    divisor = 0x988000
    for i in range(16):
        if data32 & 1 << (23 - i):
            data32 ^= divisor
        divisor >>= 1
    return data32


i2c0 = I2C(0, scl=Pin(17), sda=Pin(16), freq=100*1000)

buf = bytearray([0xE3])
i2c0.writeto(0x40, buf, False)
read = i2c0.readfrom(0x40, 3, True)
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)

data16 = (msb << 8) | (lsb & 0xFC)
temp = (-46.85 + (175.72 * data16 / (1 << 16)))
print("Temperature C ", temp)
print("Checksum=", crcCheck(msb, lsb, check))

buf = bytearray([0xF5])
i2c0.writeto(0x40, buf, True)
read = bytearray(3)
while True:
    sleep_ms(1)
    try:
        i2c0.readfrom_into(0x40, read, True)
        break
    except:
        continue
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)
data16 = (msb << 8) | (lsb & 0xFC)
hum = -6 + (125.0 * data16) / 65536
print("Humidity ", hum)
print("Checksum=", crcCheck(msb, lsb, check))

Page 190

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def blink():
    label("again")
    set(pins, 1)
    set(pins, 0)
    jmp("again")


sm = rp2.StateMachine(0, blink, freq=2000, set_base=Pin(16))
sm.active(1)

Page 193

import rp2
from machine import Pin

@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def blink():
    label("again")
    set(pins, 1)
    set(x,31)
    label("loop1")
    nop() [31]
    jmp(x_dec,"loop1")  
    set(pins, 0)  
    set(x,31)
    label("loop2")
    nop() [31]
    jmp(x_dec,"loop2") 
    jmp("again")  


sm = rp2.StateMachine(0, blink, freq=2000, set_base=Pin(16))
sm.active(1)

Page 194

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def squarewave():
    pull(block)
    label("again")
    set(pins, 1)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pins, 0)
    mov(x, osr)
    label("loop2")
    jmp(x_dec, "loop2")
    jmp("again")


sm = rp2.StateMachine(0, squarewave, freq=2000, set_base=Pin(16))
sm.active(1)
sm.put(0xFFF)

Page 196

import rp2
from machine import Pin


@rp2.asm_pio(out_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW))
def output():
    pull(block)
    label("again")
    out(pins, 2)
    jmp("again")


sm = rp2.StateMachine(0, output, freq=2000, out_base=Pin(
    16), out_shiftdir=rp2.PIO.SHIFT_RIGHT)
sm.active(1)
sm.put(0xFEDCBA98)

Page 198

import rp2
from machine import Pin


@rp2.asm_pio(out_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW), autopull=True)
def output():
    label("again")
    out(pins, 2)
    jmp("again")


sm = rp2.StateMachine(0, output, freq=2000, out_base=Pin(
    16), out_shiftdir=rp2.PIO.SHIFT_RIGHT)
sm.active(1)
while True:
    sm.put(0xFEDCBA98)

Page 200

import rp2
from machine import Pin

@rp2.asm_pio(sideset_init=rp2.PIO.OUT_LOW)
def squarewave():
    label("again")    
    nop().side(1)
    jmp("again").side(0) 

sm = rp2.StateMachine(0, squarewave, freq=2000,sideset_base=Pin(16))
sm.active(1)

Page 200

import rp2
from machine import Pin


@rp2.asm_pio(sideset_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW))
def squarewave():
    label("again")
    nop().side(2)
    jmp("again").side(1)


sm = rp2.StateMachine(0, squarewave, freq=2000, sideset_base=Pin(16))
sm.active(1)

Page 202

import rp2
from machine import Pin


@rp2.asm_pio()
def light():
    label("again")
    in_(pins, 1)
    push(block)
    jmp("again")


LED = Pin(25, mode=Pin.OUT)
in1 = Pin(16, mode=Pin.IN)
sm = rp2.StateMachine(0, light, freq=2000, in_base=Pin(16))
sm.active(1)
while True:
    flag = sm.get()
    if (flag == 0):
        LED.value(0)
    else:
        LED.value(1)

Page 204

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW)
def squarewave():
    label("again")
    wait(0, pin, 0)
    wait(1, pin, 0)
    set(pins, 1)
    set(pins, 0)
    jmp("again")


in1 = Pin(16, mode=Pin.IN)
sm = rp2.StateMachine(0, squarewave, freq=2000,
                      in_base=Pin(16), set_base=Pin(17))
sm.active(1)

Page 217

from machine import Pin
from utime import sleep_ms, ticks_us


class DHT22():
    def __init__(self, gpio):
        self.pin = gpio
        self.pin = Pin(2, mode=Pin.OUT)
        self.pin.high()
        self.checksum = 0
        self.temperature = 0
        self.humidity = 0
        sleep_ms(1)

    def getReading(self):
        DHT = self.pin
        DHT.low()
        sleep_ms(1)
        DHT.init(mode=Pin.IN)
        for i in range(2):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass

        data = 0
        t1 = ticks_us()
        for i in range(32):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass
            t2 = ticks_us()
            data = data << 1
            data = data | ((t2 - t1) > 100)
            t1 = t2

        checksum = 0
        for i in range(8):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass
            t2 = ticks_us()
            checksum = checksum << 1
            checksum = checksum | ((t2 - t1) > 100)
            t1 = t2
        byte1 = (data >> 24 & 0xFF)
        byte2 = (data >> 16 & 0xFF)
        byte3 = (data >> 8 & 0xFF)
        byte4 = (data & 0xFF)
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)

Page 220

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, autopush=True, in_shiftdir=rp2.PIO.SHIFT_RIGHT)
def dht22():
    wrap_target()
    label("again")
    pull(block)
    set(pins, 0)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 0)

    wait(1, pin, 0)
    wait(0, pin, 0)
    wait(1, pin, 0)
    wait(0, pin, 0)

    set(y, 31)
    label("bits")
    wait(1, pin, 0)
    set(x, 0)
    label("loop2")
    jmp(x_dec, "continue")
    label("continue")
    jmp(pin, "loop2")
    in_(x, 4)
    jmp(y_dec, "bits")

    set(y, 7)
    label("check")
    wait(1, pin, 0)
    set(x, 0)
    label("loop3")
    jmp(x_dec, "continue2")
    label("continue2")
    jmp(pin, "loop3")
    in_(x, 4)
    jmp(y_dec, "check")
    wrap()


class DHT22():
    def __init__(self, gpio):
        self.sm = rp2.StateMachine(0, dht22, freq=976562, in_base=Pin(
            gpio), set_base=Pin(gpio), jmp_pin=Pin(gpio))
        self.sm.active(1)

    def getByte(self):
        count = self.sm.get()
        byte = 0
        for i in range(8):
            byte = byte << 1
            if ((count >> i * 4) & 0x0F) > 8:
                byte = byte | 1
        return byte

    def getReading(self):
        self.sm.put(1000)
        byte1 = self.getByte()
        print(byte1)
        byte2 = self.getByte()
        byte3 = self.getByte()
        print(hex(byte2))
        byte4 = self.getByte()
        checksum = self.getByte()
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)

Page 226

import rp2
from machine import Pin


@rp2.asm_pio(set_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW), autopush=True, in_shiftdir=rp2.PIO.SHIFT_LEFT)
def dht22():
    wrap_target()
    label("again")
    pull(block)
    set(pins, 0)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 0)

    wait(1, pin, 0)
    wait(0, pin, 0)
    wait(1, pin, 0)
    wait(0, pin, 0)

    set(y, 31)
    label("bits")
    wait(1, pin, 0)[25]
    in_(pins, 1)
    wait(0, pin, 0)
    jmp(y_dec, "bits")

    set(y, 7)
    label("check")
    wait(1, pin, 0)[25]
    set(pins, 2)
    set(pins, 0)
    in_(pins, 1)
    wait(0, pin, 0)
    jmp(y_dec, "check")
    push(block)
    wrap()


class DHT22():
    def __init__(self, gpio):
        self.sm = rp2.StateMachine(0, dht22, freq=490196, in_base=Pin(
            gpio), set_base=Pin(gpio), jmp_pin=Pin(gpio))
        self.sm.active(1)

    def getReading(self):
        self.sm.put(500)
        data = 0
        data = self.sm.get()
        byte1 = (data >> 24 & 0xFF)
        byte2 = (data >> 16 & 0xFF)
        byte3 = (data >> 8 & 0xFF)
        byte4 = (data & 0xFF)
        checksum = self.sm.get() & 0xFF
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)

Page 245

from utime import sleep_ms, sleep_us
from machine import Pin
from time import sleep


class DS18B20:
    def __init__(self, pin):
        self.pin = Pin(pin, mode=Pin.IN)
        self.pin.high()

    def presence(self):
        self.pin.init(mode=Pin.OUT)
        self.pin.high()
        sleep_ms(1)
        self.pin.low()
        sleep_us(480)
        self.pin.init(mode=Pin.IN)
        sleep_us(70)
        b = self.pin.value()
        sleep_us(410)
        return b

    @micropython.native
    def writeBit(self, b):
        if b == 1:
            delay1 = 1
            delay2 = 30
        else:
            delay1 = 30
            delay2 = 0
        self.pin.low()
        for i in range(delay1):
            pass
        self.pin.high()
        for i in range(delay2):
            pass

    def writeByte(self, byte):
        self.pin.init(mode=Pin.OUT)
        for i in range(8):
            self.writeBit(byte & 1)
            byte = byte >> 1
        self.pin.init(mode=Pin.IN)

    @micropython.native
    def readBit(self):
        self.pin.init(mode=Pin.OUT)
        self.pin.low()
        self.pin.high()
        self.pin.init(mode=Pin.IN)
        b = self.pin.value()
        sleep_us(60)
        return b

    def readByte(self):
        byte = 0
        for i in range(8):
            byte = byte | self.readBit() << i
        return byte

    def convert(self):
        self.writeByte(0x44)
        for i in range(500):
            sleep_ms(10)
            if self.readBit() == 1:
                j = i
                break
        return j

    def crc8(self, data, len):
        crc = 0
        for i in range(len):
            databyte = data[i]
            for j in range(8):
                temp = (crc ^ databyte) & 0x01
                crc >>= 1
                if temp:
                    crc ^= 0x8C
                databyte >>= 1
        return crc

    def getTemp(self):
        if self.presence() == 1:
            return -1000
        self.writeByte(0xCC)
        if self.convert() == 500:
            return -3000
        self.presence()
        self.writeByte(0xCC)
        self.writeByte(0xBE)
        data = []
        for i in range(9):
            data.append(self.readByte())
        if self.crc8(data, 9) != 0:
            return -2000
        t1 = data[0]
        t2 = data[1]
        temp1 = (t2 << 8 | t1)
        if t2 & 0x80:
            temp1 = temp1 | 0xFFFF0000
        return temp1/16


dS18B20 = DS18B20(2)
if dS18B20.presence() == 1:
    print("No device")
else:
    print("Device present")

print(dS18B20.getTemp())

Page 253

import rp2
from machine import Pin
from utime import sleep_ms


@rp2.asm_pio(set_init=rp2.PIO.OUT_HIGH, out_init=rp2.PIO.OUT_HIGH, autopush=True, push_thresh=8)
def DS1820():
    wrap_target()
    label("again")
    pull(block)
    mov(x, osr)
    jmp(not_x, "read")
    label("write")
    set(pindirs, 1)
    set(pins, 0)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 2)[31]
    wait(1, pin, 0)[31]

    pull(block)
    mov(x, osr)
    label("bytes1")
    pull(block)
    set(y, 7)
    set(pindirs, 3)
    label("bit1")
    set(pins, 0)[1]
    out(pins, 1)[31]
    set(pins, 1)[20]
    jmp(y_dec, "bit1")
    jmp(x_dec, "bytes1")
    set(pindirs, 0)[31]
    jmp("again")

    label("read")
    pull(block)
    mov(x, osr)
    label("bytes2")
    set(y, 7)
    label("bit2")
    set(pindirs, 1)
    set(pins, 0)[1]
    set(pindirs, 0)[5]
    in_(pins, 1)[10]
    jmp(y_dec, "bit2")
    jmp(x_dec, "bytes2")
    wrap()


class DS18B20:
    def __init__(self, pin):
        self.sm = rp2.StateMachine(0, DS1820, freq=490196, set_base=Pin(2), out_base=Pin(
            2), in_base=Pin(2), out_shiftdir=rp2.PIO.SHIFT_RIGHT, in_shiftdir=rp2.PIO.SHIFT_RIGHT)
        self.sm.active(1)

    def writeBytes(self, bytes, len):
        self.sm.put(250)
        self.sm.put(len-1)
        for i in range(len):
            self.sm.put(bytes[i])

    def readBytes(self, len):
        self.sm.put(0)
        self.sm.put(len-1)
        bytes = []
        for i in range(len):
            bytes.append(self.sm.get() >> 24)
        return bytes

    def getTemp(self):
        self.writeBytes([0xCC, 0x44], 2)
        sleep_ms(1000)
        self.writeBytes([0xCC, 0xBE], 2)
        data = self.readBytes(9)
        t1 = data[0]
        t2 = data[1]
        temp1 = (t2 << 8 | t1)
        if t2 & 0x80:
            temp1 = temp1 | 0xFFFF0000
        return temp1/16


dS18B20 = DS18B20(2)
print(dS18B20.getTemp())

Page 263

from machine import UART, Pin
from utime import sleep_ms

uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("Hello World \n", "utf-8")
uart.write(SendData)
RecData = uart.read()
print(RecData)

Page 264

from machine import UART, Pin
from utime import sleep_ms

uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("A"*32, "utf-8")
uart.write(SendData)
sleep_ms(500)
RecData = uart.read(32)
print(RecData)

Page 266

from machine import UART, Pin, mem32
from utime import sleep_ms


def uart_read(uart):
    rxData = bytes()
    while uart.any() > 0:
        rxData += uart.read(1)
    return rxData


uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("A"*65, "utf-8")
uart.write(SendData)
sleep_ms(500)
RecData = uart_read(uart)
print(RecData)
print(len(RecData))

Page 276

from utime import ticks_us, sleep_ms
from machine import UART, Pin


def uart_read(uart, timeout, interchar):
    rxData = bytes()
    t = ticks_us()
    while True:
        if uart.any() > 0:
            break
        if ticks_us()-t > timeout:
            return None
    while True:
        while uart.any() > 0:
            rxData += uart.read(1)
            t = ticks_us()
        if ticks_us()-t > interchar:
            break
    return rxData.decode("utf-8")


def initWiFi(uartNo):
    uart = UART(uartNo, baudrate=115200, bits=8, stop=1,
                parity=None, rx=Pin(5), tx=Pin(4))
    sleep_ms(100)
    return uart


def ATWiFi(uart):
    SendData = "AT\r\n"
    uart.write(SendData)
    return uart_read(uart, 10000, 100)


uart = initWiFi(1)
response = ATWiFi(uart)
print(response)

Page 288

from utime import ticks_us, sleep_ms
from machine import UART, Pin


class WiFi:
    def __init__(self, uartNo, tx, rx):
        self.uart = UART(uartNo, baudrate=115200, bits=8, stop=1,
                         parity=None, rx=Pin(rx), tx=Pin(tx))
 
 
    def _read(self, timeout, interchar):
        rxData = bytearray(2000)
        t = ticks_us()
        while True:
            if self.uart.any() > 0:
                break
            if ticks_us()-t > timeout:
                return None
        while True:
            while self.uart.any() > 0:
                rxData += self.uart.read(1)
                t = ticks_us()
            if ticks_us()-t > interchar:
                break
        return rxData.decode("utf-8")

    def AT(self):
        self.uart.write(b"AT\r\n")
        return self._read(10000, 100)

    def getVersion(self):
        self.uart.write("AT+GMR\r\n")
        return self._read(10000, 100)

    def reset(self):
        self.uart.write("AT+RST\r\n")
        print(self._read(10000, 10000))
        return self._read(10000, 10000)

    def setUART(self, baud):
        self.uart.write("AT+UART_CUR="+str(baud)+",8,1,0,0\r\n")
        return self._read(10000, 100)

    def mode(self, mode):
        command = "AT+CWMODE_CUR="+str(mode)+"\r\n"
        self.uart.write(command)
        return self._read(10000, 100)

    def scan(self):
        self.uart.write("AT+CWLAP\r\n")
        return self._read(100000, 1000*1000*20)

    def scandisplay(self):
        self.uart.write("AT+CWLAP\r\n")
        block = self._read(10000, 100)
        print(block)
        for i in range(20):
            block = self._read(1000*1000*20, 100)
            if block == None:
                break
            if block.find("OK") >= 0:
                break
            print(block)

    def connect(self, ssid, password):
        command = "AT+CWJAP_CUR=" + '"' + ssid+'"' + ","+'"'+password+'"' + "\r\n"
        self.uart.write(command)
        for i in range(20):
            block = self._read(1000*1000*20, 100)
            if block == None:
                break
            if block.find("OK") >= 0:
                break
        print("connected")

    def getIP(self):
        self.uart.write("AT+CIFSR\r\n")
        return self._read(100000, 100)

    def getWebPage(self, URL, page):
        command = 'AT+CIPSTART="TCP",'+'"'+URL+'"'+",80\r\n"
        self.uart.write(command)
        block = self._read(1000*1000*2, 1000*1000)
        if block.find("OK") < 0:
            return -1
        command = 'GET ' + page + ' HTTP/1.1\r\nHost:'+URL+'\r\n\r\n'
        command2 = "AT+CIPSEND="+str(len(command)) + "\r\n"
        self.uart.write(command2)
        block = self._read(1000*1000*8, 1000*1000*1)
        if block.find(">") < 0:
            return -1
        self.uart.write(command)
        block = self._read(1000*1000*5, 1000*1000*1)
        return block

    def startServer(self):
        self.uart.write("AT+CIPMUX=1\r\n")
        response = self._read(1000*1000*5, 1000)
        print("mux set", response)
        if response.find("OK") < 0:
            return -1
        self.uart.write("AT+CIPSERVER=1,80\r\n")
        response = self._read(1000*1000*5, 1000)
        if response.find("OK") < 0:
            return -1
        print("ready for clients", response)

        while True:
            block = self._read(1000*1000*5, 100)
            if block == None:
                continue
            if block.find("+IPD") < 0:
                continue

            n = block.find("+IPD,")+5
            m = block.find(",", n)
            id = block[n:m]

            data = "HTTP/1.0 200 OK\r\nServer: Pico\r\nContent-type: text/html\r\n\r\n<html><head><title>Temperature</title></head><body><p>{\"humidity\":81%,\"airtemperature\":23.5C}</p></body></html>\r\n"
            command = "AT+CIPSEND="+id+","+str(len(data))+"\r\n"

            self.uart.write(command)
            response = self._read(1000*1000*5, 1000*1000*1)
            if response.find(">") < 0:
                return -1
            self.uart.write(data)
            response = self._read(1000*1000*5, 1000*1000*1)
            if response.find("OK") < 0:
                return -1
            command = "AT+CIPCLOSE="+id+"\r\n"
            self.uart.write(command)
            response = self._read(1000*1000*5, 1000*1000*1)
            if response.find("OK") < 0:
                return -1


wifi = WiFi(1, 4, 5)
print(wifi.AT())
response = wifi.mode(1)
print("mode", response)
wifi.connect("SSID", "password")
print(wifi.startServer())

Page 296

from machine import mem32, Pin
from time import sleep_ms
led = Pin(25, mode=Pin.OUT)
addrSIO = 0xd0000000
while True:
    mem32[addrSIO + 0x014] = 1 << 25
    sleep_ms(500)
    mem32[addrSIO + 0x018] = 1 << 25
    sleep_ms(500)

Page 298

from machine import Pin
import machine


def gpio_get():
    return machine.mem32[0xd0000000+0x010]


def gpio_set(value, mask):
    machine.mem32[0xd0000000+0x01C] =
    (machine.mem32[0xd0000000+0x010]) ^ value & mask


pin = Pin(22, Pin.OUT)
pin = Pin(21, Pin.OUT)
value1 = 1 << 22 | 0 << 21
value2 = 0 << 22 | 1 << 21
mask = 1 << 22 | 1 << 21
while True:
    gpio_set(value1, mask)
    gpio_set(value2, mask)

Program Listings

Programmer’s Python: Async

pythonAsync360

 

We have decided not to make the programs available as a download because this is not the point of the book - the programs are not finished production code but something you should type in and study.

The best solution is to provide the source code of the programs in a form that can be copied and pasted into Thonny or VS Code project. 

The only downside is that you have to create a project to paste the code into.

To do this follow the instructions in the book.

All of the programs below were copy and pasted from working programs in the IDE. They have been formatted using the built in formatter and hence are not identical in layout to the programs in the book. This is to make copy and pasting them easier. The programs in the book are formatted to be easy to read on the page.

If anything you consider important is missing or if you have any requests or comments  contact:

This email address is being protected from spambots. You need JavaScript enabled to view it. 

Page 49

import multiprocessing


def myProcess():
    print("Hello Process World")


if __name__ == '__main__':
    p1 = multiprocessing.Process(target=myProcess)
    p1.start()

 

Page 52

import multiprocessing


def myProcess():
    while True:
        pass


if __name__ == '__main__':
    p0 = multiprocessing.current_process()
    p1 = multiprocessing.Process(target=myProcess, daemon=True)
    p2 = multiprocessing.Process(target=myProcess, daemon=False)
    p1.start()
    p2.start()
    print(p0.pid)
    print(p1.pid)
    print(p2.pid)
    print("ending")

Page 55

import multiprocessing
import multiprocessing.connection
import random
import time


def myProcess():
    time.sleep(random.randrange(1, 4))


if __name__ == '__main__':
    p1 = multiprocessing.Process(target=myProcess)
    p2 = multiprocessing.Process(target=myProcess)
    p3 = multiprocessing.Process(target=myProcess)
    p1.start()
    p2.start()
    p3.start()

    waitList = [p1.sentinel, p2.sentinel, p3.sentinel]
    res = multiprocessing.connection.wait(waitList)
    print(res)
    print(waitList.index(res[0])+1)

Page 57

import time
import multiprocessing


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    print(4*pi)


if __name__ == '__main__':
    N = 10000000
    p1 = multiprocessing.Process(target=myPi, args=(N//4+1, N//4*2))
    p2 = multiprocessing.Process(target=myPi, args=(N//4*2+1, N//4*3))
    p3 = multiprocessing.Process(target=myPi, args=(N//4*3+1, N))

    t1 = time.perf_counter()
    p1.start()
    p2.start()
    p3.start()
    myPi(1, N//4)
    p1.join()
    p2.join()
    p3.join()
    t2 = time.perf_counter()
    print((t2-t1)*1000)

Page 64

import time
import multiprocessing


def myPi(m, n):
    pi = 0
    s = -1
    for k in range(m, n):
        s = -1*s
        pi += s / (2 * k - 1)
    print(4*pi)


if __name__ == '__main__':
    import multiprocessing
    import multiprocessing.connection
    import time
    N = 1000000
    p1 = multiprocessing.Process(target=myPi, args=(N//2+1, N))
    t1 = time.perf_counter()
    p1.start()
    myPi(1, N//2)
    p1.join()
    t2 = time.perf_counter()
    print((t2-t1)*1000)

Page 72

import threading


def myThread():
    while True:
        pass


t0 = threading.main_thread()
t1 = threading.Thread(target=myThread, daemon=True)
t2 = threading.Thread(target=myThread, daemon=False)
t1.start()
t2.start()
print(t0.native_id)
print(t1.native_id)
print(t2.native_id)
print("ending")

Page 74 

import threading


def myThread(sym):
    temp = sym
    while True:
        print(temp)


t1 = threading.Thread(target=myThread, args=("A",))
t2 = threading.Thread(target=myThread, args=("B",))
t1.start()
t2.start()
t1.join()

Page 75
import threading


def myThread(sym):
    myThread.temp = sym
    while True:
        print(myThread.temp)


myThread.temp = ""

t1 = threading.Thread(target=myThread, args=("A",))
t2 = threading.Thread(target=myThread, args=("B",))
t1.start()
t2.start()
t1.join()
Page 76
import threading


class MyClass():
    temp = ""


def myThread(sym):
    myObject = MyClass()
    myObject.temp = sym
    while True:
        print(myObject.temp)


t1 = threading.Thread(target=myThread, args=("A",))
t2 = threading.Thread(target=myThread, args=("B",))
t1.start()
t2.start()
t1.join()

Page 77

import threading

myObject = threading.local()


def myThread(sym):
    myObject.temp = sym
    while True:
        print(myObject.temp)


t1 = threading.Thread(target=myThread, args=("A",))
t2 = threading.Thread(target=myThread, args=("B",))
t1.start()
t2.start()
t1.join()
Page 78

 

import threading
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    print(4*pi)


N = 10000000
thread1 = threading.Thread(target=myPi, args=(N//2+1, N))
t1 = time.perf_counter()
thread1.start()
myPi(1, N//2)
thread1.join()
t2 = time.perf_counter()
print((t2-t1)*1000)
 
Page 79
import urllib.request
import time


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')


t1 = time.perf_counter()
download()
download()
t2 = time.perf_counter()
print((t2-t1)*1000)
Page 80
import urllib.request
import threading
import time


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')


thread1 = threading.Thread(target=download)
t1 = time.perf_counter()
thread1.start()
download()
thread1.join()
t2 = time.perf_counter()
print((t2-t1)*1000)
Page 81
import threading
import time


def test():
    while (True):
        time.sleep(0)
        pass


thread1 = threading.Thread(target=test)
thread2 = threading.Thread(target=test)
thread1.start()
thread2.start()
thread1.join()

Page 87 

from cmath import sqrt
import threading
import time

myCounter = 0


def count():
    global myCounter
    for i in range(100000):
        temp = myCounter+1
        x = sqrt(2)
        myCounter = temp


thread1 = threading.Thread(target=count)
thread2 = threading.Thread(target=count)
t1 = time.perf_counter()

thread1.start()
thread2.start()
thread1.join()
thread2.join()

t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter)

 

Page 90 (top)
from cmath import sqrt
import threading
import time

myCounter = 0
countlock = threading.Lock()


def count():
    global myCounter
    for i in range(100000):
        countlock.acquire()
        temp = myCounter+1
        x = sqrt(2)
        myCounter = temp
        countlock.release()


thread1 = threading.Thread(target=count)
thread2 = threading.Thread(target=count)
t1 = time.perf_counter()

thread1.start()
thread2.start()
thread1.join()
thread2.join()

t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter)
 
Page 90 (Bottom)
from cmath import sqrt
import threading
import time

myCounter = 0
countlock = threading.Lock()


def count():
    global myCounter
    countlock.acquire()
    for i in range(100000):
        temp = myCounter+1
        x = sqrt(2)
        myCounter = temp
    countlock.release()


thread1 = threading.Thread(target=count)
thread2 = threading.Thread(target=count)
t1 = time.perf_counter()

thread1.start()
thread2.start()
thread1.join()
thread2.join()

t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter)
Page 91
import multiprocessing
import time


def myProcess(lock):
    lock.acquire()
    time.sleep(4)
    lock.release()


if __name__ == '__main__':
    myLock = multiprocessing.Lock()
    p1 = multiprocessing.Process(target=myProcess, args=(myLock,))
    p2 = multiprocessing.Process(target=myProcess, args=(myLock,))
    t1 = time.perf_counter()
    p1.start()
    p2.start()
    p1.join()
    p2.join()
    t2 = time.perf_counter()
    print((t2-t1)*1000)
Page 92-93

import threading
import time

countlock1 = threading.Lock()
countlock2 = threading.Lock()
myCounter1 = 0
myCounter2 = 0


def count1():
    global myCounter1
    global myCounter2
    for i in range(100000):
        countlock1.acquire()
        myCounter1 += 1
        countlock2.acquire()
        myCounter2 += 1
        countlock2.release()
        countlock1.release()


def count2():
    global myCounter1
    global myCounter2
    for i in range(100000):
        countlock2.acquire()
        myCounter2 += 1
        countlock1.acquire()
        myCounter1 += 1
        countlock1.release()
        countlock2.release()


thread1 = threading.Thread(target=count1)
thread2 = threading.Thread(target=count2)
t1 = time.perf_counter()

thread1.start()
thread2.start()
thread1.join()
thread2.join()

t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter1)

Page 95

import threading
import time

countlock1 = threading.Lock()
countlock2 = threading.Lock()
myCounter1 = 0
myCounter2 = 0


def count1():
    global myCounter1
    global myCounter2
    for i in range(100000):
        countlock1.acquire()
        myCounter1 += 1
        if countlock2.acquire(timeout=0.01):
            myCounter2 += 1
            countlock2.release()
        countlock1.release()


def count2():
    global myCounter1
    global myCounter2
    for i in range(100000):
        countlock2.acquire()
        myCounter2 += 1
        if countlock1.acquire(timeout=0.01):
            myCounter1 += 1
            countlock1.release()
        countlock2.release()


thread1 = threading.Thread(target=count1)
thread2 = threading.Thread(target=count2)
t1 = time.perf_counter()

thread1.start()
thread2.start()
thread1.join()
thread2.join()

t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter1)

Page 105

import threading
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    global PI
    with myLock:
        PI += pi*4


PI = 0
N = 10000000
myLock = threading.Lock()
thread1 = threading.Thread(target=myPi, args=(N//2+1, N))
t1 = time.perf_counter()
thread1.start()
myPi(1, N//2)
thread1.join()
t2 = time.perf_counter()
print((t2-t1)*1000)
print(PI)

time.perf_counter()

print((t2-t1)*1000)
print(PI)

Page 107

 
import threading
import time


def myThread1():
    time.sleep(1)
    thread2.join()


def myThread2():
    time.sleep(1)
    thread1.join()


thread1 = threading.Thread(target=myThread1)
thread2 = threading.Thread(target=myThread2)
thread1.start()
thread2.start()

Page 108

 
import threading
import time

joinLock = threading.Lock()


def myThread1():
    time.sleep(1)
    joinLock.release()


thread1 = threading.Thread(target=myThread1)
joinLock.acquire()
thread1.start()
joinLock.acquire()

Page 109

 
import urllib.request
import threading


def download(html, lock):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    lock.release()


html1 = []
html2 = []
mySem = threading.Semaphore()

thread1 = threading.Thread(target=download, args=(html1, mySem))
thread2 = threading.Thread(target=download, args=(html2, mySem))


mySem.acquire()
thread1.start()
thread2.start()
mySem.acquire()

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")

Page 111

 
import urllib.request
import threading


def download(html, event):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    event.set()


html1 = []
html2 = []
myEvent = threading.Event()

thread1 = threading.Thread(target=download, args=(html1, myEvent))
thread2 = threading.Thread(target=download, args=(html2, myEvent))


myEvent.clear()
thread1.start()
thread2.start()
myEvent.wait()

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")

Page 112

 
import urllib.request
import threading


def download(html, barrier):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    barrier.wait()


html1 = []
html2 = []
myBarrier = threading.Barrier(3)

thread1 = threading.Thread(target=download, args=(html1, myBarrier))
thread2 = threading.Thread(target=download, args=(html2, myBarrier))

thread1.start()
thread2.start()
myBarrier.wait()

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")

Page 113

 
import urllib.request
import threading


def download(html, barrier):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    try:
        barrier.wait()
    except:
        pass


html1 = []
html2 = []
myBarrier = threading.Barrier(2)

thread1 = threading.Thread(target=download, args=(html1, myBarrier))
thread2 = threading.Thread(target=download, args=(html2, myBarrier))

thread1.start()
thread2.start()
myBarrier.wait()
myBarrier.abort()

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")

Page 116

 
import urllib.request
import threading


def download(html, condition):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    with condition:
        condition.notify()


html1 = []
html2 = []

myCondition = threading.Condition()

thread1 = threading.Thread(target=download, args=(html1, myCondition))
thread2 = threading.Thread(target=download, args=(html2, myCondition))

thread1.start()
thread2.start()
with myCondition:
    myCondition.wait()

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")

Page 118

 
import urllib.request
import threading


def download(html, condition):
    with urllib.request.urlopen('http://www.example.com/') as f:
        html.append(f.read().decode('utf-8'))
    global myCount
    with condition:
        myCount += 1
        condition.notify()


myCount = 0

html1 = []
html2 = []
html3 = []

myCondition = threading.Condition(threading.Lock())

thread1 = threading.Thread(target=download, args=(html1, myCondition))
thread2 = threading.Thread(target=download, args=(html2, myCondition))
thread3 = threading.Thread(target=download, args=(html3, myCondition))
thread1.start()
thread2.start()
thread3.start()
with myCondition:
    myCondition.wait_for(lambda: myCount >= 2)

if (html1 != []):
    print("thread1")
if (html2 != []):
    print("thread2")
if (html3 != []):
    print("thread3")

Page 125

import multiprocessing


def addCount(q):
    for i in range(1000):
        q.put(i)


def getCount(q, l):
    while True:
        i = q.get()
        with l:
            print(i)


if __name__ == '__main__':
    q = multiprocessing.Queue()
    pLock = multiprocessing.Lock()

    p1 = multiprocessing.Process(target=addCount, args=(q,))
    p2 = multiprocessing.Process(target=getCount, args=(q, pLock))
    p3 = multiprocessing.Process(target=getCount, args=(q, pLock))
    p1.start()
    p2.start()
    p3.start()

    p3.join()

Page 128-129

import multiprocessing
from time import sleep


def addCount(con):
    for i in range(500):
        con.send(i)


def getCount(con, l):
    while True:
        sleep(0.005)
        i = con.recv()
        with l:
            print(i, multiprocessing.current_process().name)


if __name__ == '__main__':

    con1, con2 = multiprocessing.Pipe()
    pLock = multiprocessing.Lock()

    p1 = multiprocessing.Process(target=addCount, args=(con1,))
    p2 = multiprocessing.Process(target=getCount, args=(con2, pLock))
    p3 = multiprocessing.Process(target=getCount, args=(con2, pLock))
    p1.start()
    p2.start()
    p3.start()

    p2.join()

Page 131

import time
import multiprocessing
import ctypes


def myUpdate(val):
    for i in range(1000):
        time.sleep(0.005)
        val.value += 1


if __name__ == '__main__':
    myValue = multiprocessing.Value(ctypes.c_int, 0)
    p1 = multiprocessing.Process(target=myUpdate, args=(myValue,))
    p2 = multiprocessing.Process(target=myUpdate, args=(myValue,))
    p2.start()
    p1.start()
    p1.join()
    p2.join()
    print(myValue.value)

Page 135 

import time
import multiprocessing
import multiprocessing.shared_memory


def myUpdate(name, lock):
    mySharedMem = multiprocessing.shared_memory.SharedMemory(
        create=False, name=name)
    for i in range(127):
        time.sleep(0.005)
        with lock:
            mySharedMem.buf[0] = mySharedMem.buf[0]+1
    mySharedMem.close()


if __name__ == '__main__':
    mylock = multiprocessing.Lock()
    mySharedMem = multiprocessing.shared_memory.SharedMemory(
        create=True, size=10)
    mySharedMem.buf[0] = 1
    p1 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedMem.name, mylock))
    p2 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedMem.name, mylock))
    p2.start()
    p1.start()
    p1.join()
    p2.join()
    print(mySharedMem.buf[0])
    mySharedMem.close()
    mySharedMem.unlink()

Page 136

 
import time
import multiprocessing
import multiprocessing.shared_memory
import sys


def myUpdate(mySharedMem, lock):
    for i in range(1000):
        time.sleep(0.005)
        with lock:
            count = int.from_bytes(
                mySharedMem.buf[0:8], byteorder=sys.byteorder)
            count = count+1
            mySharedMem.buf[0:8] = int.to_bytes(
                count, 8, byteorder=sys.byteorder)
    mySharedMem.close()


if __name__ == '__main__':
    mylock = multiprocessing.Lock()
    mySharedMem = multiprocessing.shared_memory.SharedMemory(
        create=True, size=10)
    mySharedMem.buf[0:8] = int.to_bytes(1, 8,
                                        byteorder=sys.byteorder)
    p1 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedMem, mylock))
    p2 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedMem, mylock))
    p2.start()
    p1.start()
    p1.join()
    p2.join()
    count = count = int.from_bytes(mySharedMem.buf[0:8],
                                   byteorder=sys.byteorder)
    print(count)
    mySharedMem.close()
    mySharedMem.unlink()

Page 138

 
import time
import multiprocessing
import multiprocessing.shared_memory


def myUpdate(mySharedList, lock):
    for i in range(1000):
        time.sleep(0.005)
        with lock:
            mySharedList[0] = mySharedList[0]+1
    mySharedList.shm.close()


if __name__ == '__main__':
    mylock = multiprocessing.Lock()
    mySharedList = multiprocessing.shared_memory.ShareableList(
        sequence=[1])
    p1 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedList, mylock))
    p2 = multiprocessing.Process(target=myUpdate,
                                 args=(mySharedList, mylock))
    p2.start()
    p1.start()
    p1.join()
    p2.join()
    print(mySharedList[0])
    mySharedList.shm.close()
    mySharedList.shm.unlink()

Page 139

 import time
import multiprocessing
import multiprocessing.shared_memory
import multiprocessing.managers


def myUpdate(mySharedList, lock):
    for i in range(1000):
        time.sleep(0.005)
        with lock:
            mySharedList[0] = mySharedList[0]+1
    mySharedList.shm.close()


if __name__ == '__main__':
    mylock = multiprocessing.Lock()
    with multiprocessing.managers.SharedMemoryManager() as smm:
        mySharedList = smm.ShareableList([1])
        p1 = multiprocessing.Process(target=myUpdate,
                                     args=(mySharedList, mylock))
        p2 = multiprocessing.Process(target=myUpdate,
                                     args=(mySharedList, mylock))
        p2.start()
        p1.start()
        p1.join()
        p2.join()
        print(mySharedList[0])

Page 139

 
import ctypes
import multiprocessing
import time


def myPi(m, n, PI):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    with PI:
        PI.value += pi*4


if __name__ == '__main__':
    N = 10000000
    PI = multiprocessing.Value(ctypes.c_double, 0.0)
    p1 = multiprocessing.Process(target=myPi, args=(N//2+1, N, PI))
    t1 = time.perf_counter()
    p1.start()
    myPi(1, N//2, PI)
    p1.join()
    t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(PI.value)

Page 144

 
import multiprocessing.pool
import multiprocessing
import random
import time


def myProcess():
    time.sleep(random.randrange(1, 4))
    print(multiprocessing.current_process().name)


if __name__ == '__main__':
    p = multiprocessing.pool.Pool(2)
    p.apply_async(myProcess)
    p.apply_async(myProcess)
    p.close()
    p.join()

Page 145 

import multiprocessing.pool
import multiprocessing
import random
import time


def myProcess():
    time.sleep(random.randrange(1, 4))
    return multiprocessing.current_process().name


def myCallback(result):
    print(result)


if __name__ == '__main__':
    p = multiprocessing.pool.Pool(2)
    p.apply_async(myProcess, callback=myCallback)
    p.apply_async(myProcess, callback=myCallback)
    p.close()
    p.join()

Page 146 

import multiprocessing.pool
import multiprocessing
import random
import time


def myProcess():
    time.sleep(random.randrange(1, 4))
    return multiprocessing.current_process().name


if __name__ == '__main__':
    with multiprocessing.pool.Pool(2) as p:
        asr1 = p.apply_async(myProcess)
        asr2 = p.apply_async(myProcess)
        result1 = asr1.get()
        result2 = asr2.get()
        print(result1, result2)

Page 147

import multiprocessing.pool
import multiprocessing
import random
import time


def myProcess():
    time.sleep(random.randrange(1, 6))
    return multiprocessing.current_process().name


if __name__ == '__main__':
    with multiprocessing.pool.Pool(2) as p:
        asr1 = p.apply_async(myProcess)
        asr2 = p.apply_async(myProcess)

        waiting = True
        while waiting:
            time.sleep(0.01)
            if (asr1.ready()):
                print(asr1.get())
                break
            if (asr2.ready()):
                print(asr2.get())
                break

Page 147-148

 
import multiprocessing
import multiprocessing.pool
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return pi*4


if __name__ == '__main__':
    N = 10000000
    with multiprocessing.pool.Pool(2) as p:
        t1 = time.perf_counter()
        asr1 = p.apply_async(myPi, args=(1, N//2))
        asr2 = p.apply_async(myPi, args=(N//2+1, N))
        PI = asr1.get()
        PI += asr2.get()
        t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(PI)

Page 149 (top)

 
import multiprocessing
import multiprocessing.pool


def myFunc(x):
    return x**2


if __name__ == '__main__':
    with multiprocessing.pool.Pool(10) as p:
        asr = p.map_async(myFunc, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
        res = asr.get()

    print(res)

Page 149 (bottom)

 
import multiprocessing
import multiprocessing.pool
import time


def myPi(r):
    m, n = r
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return pi*4


if __name__ == '__main__':
    N = 10000000
    with multiprocessing.pool.Pool(2) as p:
        t1 = time.perf_counter()
        asr = p.map_async(myPi, [(1, N//2), (N//2+1, N)])
        res = asr.get()
        t2 = time.perf_counter()

    print((t2-t1)*1000)
    PI = res[0]+res[1]
    print(PI)

Page 150

 
import multiprocessing
import multiprocessing.pool
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return pi*4


if __name__ == '__main__':
    N = 10000000
    with multiprocessing.pool.Pool(2) as p:
        t1 = time.perf_counter()
        asr = p.starmap_async(myPi, [(1, N//2), (N//2+1, N)])
        res = asr.get()
        t2 = time.perf_counter()

    print((t2-t1)*1000)
    PI = res[0]+res[1]
    print(PI)

Page 151

 
import multiprocessing
import multiprocessing.pool


def myFunc(x):
    return x**2


if __name__ == '__main__':
    with multiprocessing.pool.Pool(10) as p:
        results = p.imap(myFunc, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
        for result in results:
            print(result)

Page 152

import multiprocessing
import multiprocessing.pool


def myFunc(x):
    return x**2


if __name__ == '__main__':
    with multiprocessing.pool.Pool(10) as p:
        results = p.imap_unordered(myFunc, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
        for result in results:
            print(result)

Page 153

import functools
import multiprocessing
import multiprocessing.pool


def myFunc(x):
    return x**2


def mySum(value, item):
    return value+item


if __name__ == '__main__':
    with multiprocessing.pool.Pool(10) as p:
        asr = p.map_async(myFunc, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
        res = asr.get()
    sumsquares = functools.reduce(mySum, res)
    print(sumsquares)

Page 154

import multiprocessing
import multiprocessing.pool
import time
import ctypes


def counter():
    global count
    for i in range(10000):
        with count:
            temp = count.value+1
            count.value = temp


def setup(var):
    global count
    count = var


if __name__ == '__main__':
    myCounter = multiprocessing.Value(ctypes.c_int, 0)
    with multiprocessing.Pool(2, initializer=setup,
                              initargs=(myCounter,)) as p:

        t1 = time.perf_counter()
        asr1 = p.apply_async(counter)
        asr2 = p.apply_async(counter)
        asr1.wait()
        asr2.wait()
        t2 = time.perf_counter()
        print(myCounter.value)
    print((t2-t1)*1000)

Page 160

import multiprocessing
import multiprocessing.pool
import time


def myFunc(x):
    for i in range(len(x)):
        x[i] = x[i]**2


if __name__ == '__main__':
    man = multiprocessing.Manager()
    myList = man.list([1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
    p = multiprocessing.Process(target=myFunc, args=(myList,))
    t1 = time.perf_counter()
    p.start()
    p.join()
    t2 = time.perf_counter()

    print((t2-t1)*1000)
    print(myList)

Page 161

import multiprocessing


def count(myCounter):
    for i in range(1000):
        myCounter.value = myCounter.value+1


if __name__ == '__main__':
    man = multiprocessing.Manager()
    counter = man.Value(int, 0)

    p1 = multiprocessing.Process(target=count, args=(counter,))
    p2 = multiprocessing.Process(target=count, args=(counter,))
    p1.start()
    p2.start()
    p1.join()
    p2.join()
    print(counter.value)

Page 162

import multiprocessing


def count(myCounter):
    for i in range(1000):
        myCounter.value = myCounter.value+1


if __name__ == '__main__':
    man = multiprocessing.Manager()
    counter = man.Value(int, 0)

    p1 = multiprocessing.Process(target=count, args=(counter,))
    p2 = multiprocessing.Process(target=count, args=(counter,))
    p1.start()
    p2.start()
    p1.join()
    p2.join()
    print(counter.value)

Page 162

import multiprocessing
import time


def myPi(m, n, PI, lock):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    with lock:
        PI.value += pi*4


if __name__ == '__main__':
    N = 10000000
    man = multiprocessing.Manager()
    PI = man.Value(float, 0.0)
    myLock = man.Lock()
    p1 = multiprocessing.Process(target=myPi,
                                 args=(N//2+1, N, PI, myLock))
    t1 = time.perf_counter()
    p1.start()
    myPi(1, N//2, PI, myLock)
    p1.join()
    t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(PI.value)

Page 165-166

import multiprocessing
import multiprocessing.managers


class Point():
    def __init__(self):
        self._x = 0
        self._y = 0

    def setxy(self, x, y):
        self._x = x
        self._y = y

    def getxy(self):
        return (self._x, self._y)


def myFunc(point):
    point.setxy(42, 43)


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("point", Point)

if __name__ == '__main__':
    man = myManager()
    man.start()
    point = man.point()
    p1 = multiprocessing.Process(target=myFunc, args=(point,))
    p1.start()
    p1.join()
    print(point.getxy())

Page 168-169

import multiprocessing
import multiprocessing.managers


class Counter():
    def __init__(self):
        self.myCounter = 0

    def getCount(self):
        return self.myCounter

    def setCount(self, value):
        self.myCounter = value
    count = property(getCount, setCount)


class CounterProxy(multiprocessing.managers.BaseProxy):
    _exposed_ = ('getCount', 'setCount')

    def get(self):
        return self._callmethod('getCount')

    def set(self, value):
        return self._callmethod('setCount', (value,))
    value = property(get, set)


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("counter", callable=Counter,
                   proxytype=CounterProxy)


def count(myCounter):
    for i in range(1000):
        myCounter.value = myCounter.value+1


if __name__ == '__main__':
    man = myManager()
    man.start()
    counter = man.counter()

    p1 = multiprocessing.Process(target=count, args=(counter,))
    p2 = multiprocessing.Process(target=count, args=(counter,))
    p1.start()
    p2.start()
    p1.join()
    p2.join()

    print(counter.value)

Page 172

import multiprocessing
import multiprocessing.managers


class SharedList():
    def __init__(self):
        self.list = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

    def getData(self):
        return self.list

    def setData(self, value, index):
        self.list[index] = value


class SharedListProxy(multiprocessing.managers.BaseProxy):
    _exposed_ = ('getData', 'setData')

    def getData(self):
        return self._callmethod('getData')

    def setData(self, value, index):
        self._callmethod('setData', (value, index))


_sharedList = SharedList()


def SharedList():
    return _sharedList


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("SharedList", callable=SharedList,
                   proxytype=SharedListProxy)

if __name__ == '__main__':
    man = myManager(address=("192.168.253.14", 50000), authkey=b"password")
    s = man.get_server()
    s.serve_forever()

Page 174

import multiprocessing
import multiprocessing.managers


class SharedListProxy(multiprocessing.managers.BaseProxy):
    _exposed_ = ('getData', 'setData')

    def getData(self):
        return self._callmethod('getData')

    def setData(self, value, index):
        self._callmethod('setData', (value, index))


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("SharedList", proxytype=SharedListProxy)

if __name__ == '__main__':
    man = myManager(address=("192.168.253.14", 50000),
                    authkey=b"password")
    man.connect()
    myList = man.SharedList()
    print(myList.getData())

Page 174-175

 
import multiprocessing
import multiprocessing.managers


class Math:
    def myPi(self, m, n):
        pi = 0
        for k in range(m, n+1):
            s = 1 if k % 2 else -1
            pi += s / (2 * k - 1)
        return pi*4


_math = Math()


def getMath():
    return _math


class MathProxy(multiprocessing.managers.BaseProxy):
    _exposed_ = ("myPi",)

    def myPi(self, m, n):
        return self._callmethod('myPi', m, n)


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("math", callable=getMath, proxytype=MathProxy)

if __name__ == '__main__':
    man = myManager(address=("192.168.253.14", 50000),
                    authkey=b"password")
    s = man.get_server()
    s.serve_forever()

Page 175

import multiprocessing
import multiprocessing.managers


class MathProxy(multiprocessing.managers.BaseProxy):
    _exposed_ = ('myPi')

    def myPi(self, m, n):
        return self._callmethod('myPi', (m, n))


class myManager(multiprocessing.managers.BaseManager):
    pass


myManager.register("math", proxytype=MathProxy)

if __name__ == '__main__':
    man = myManager(address=("192.168.253.14", 50000), authkey=b"password")
    man.connect()
    math = man.math()
    print(math.myPi(1, 100))

Page 185

for Linux:

#!/bin/sh
echo "user name: "
read name
echo $name

for Windows:

@echo off
echo "User name:"
set /p id=
echo %id%

Top of Page
import subprocess

p = subprocess.Popen(["myscript.bat"],
                     stdout=subprocess.PIPE, stdin=subprocess.PIPE, text=True)
ans = p.stdout.readline()
print("message", ans)
p.stdin.write("mike\n")
ans = p.stdout.readline()
print("message", ans)
as modified at bottom of page
import subprocess

p = subprocess.Popen(["myscript.bat"],
                     stdout=subprocess.PIPE, stdin=subprocess.PIPE, text=True)
ans = p.stdout.readline()
print("message",ans)
p.stdin.write("mike\n")
p.stdin.flush()
ans = p.stdout.readline()
print("message",ans)

Page 186

import subprocess
p = subprocess.Popen(["myscript.bat"], stdout=subprocess.PIPE,
                     stdin=subprocess.PIPE, bufsize=0,
                     universal_newlines=True, text=True)

ans = p.stdout.readline()
print("message", ans)
p.stdin.write("mike\n")

ans = p.stdout.readline()
print("message", ans)

Page 189

import subprocess
import threading


class AsyncReader():
    def __init__(self, stream):
        self._stream = stream
        self._char = ""
        self.t = threading.Thread(target=self._get, daemon=True)
        self.t.start()

    def get(self):
        self.t.join(0.04)
        if self.t.is_alive():
            return ""
        else:
            result = self._char
            self.t = threading.Thread(target=self._get, daemon=True)
            self.t.start()
            return result

    def _get(self):
        self._char = self._stream.read(1)

    def readmessage(self):
        ans = ""
        while True:
            char = self.get()
            if char == "":
                break
            ans += char
        return ans


p = subprocess.Popen(["myscript.bat"],
                     stdout=subprocess.PIPE, stdin=subprocess.PIPE, bufsize=1, universal_newlines=True, text=True)

aRead = AsyncReader(p.stdout)

ans = aRead.readmessage()

print("message", ans)
p.stdin.write("mike\n")

ans = aRead.readmessage()
print("message", ans)

Page 197

import concurrent.futures
import time
import urllib.request


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
    return html


with concurrent.futures.ThreadPoolExecutor() as executor:
    t1 = time.perf_counter()
    f1 = executor.submit(download)
    f2 = executor.submit(download)
    t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(f1.result()[:25])
    print(f2.result()[:25])

Page 198 modified by top

import concurrent.futures
import time
import urllib.request


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
    return html


t1 = time.perf_counter()
with concurrent.futures.ThreadPoolExecutor() as executor:
    f1 = executor.submit(download)
    f2 = executor.submit(download)

    t2 = time.perf_counter()
    print((t2-t1)*1000)

    res = concurrent.futures.wait([f1, f2],
                                  return_when=concurrent.futures.FIRST_COMPLETED)
    for f in res.done:
        print(f.result()[:25])

Page 198 modified by bottom

import concurrent.futures
import time
import urllib.request


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
    return html


with concurrent.futures.ThreadPoolExecutor() as executor:
    f1 = executor.submit(download)
    f2 = executor.submit(download)
    for f in concurrent.futures.as_completed([f1, f2]):
        print(f.result()[:25])

Page 199

import concurrent.futures
import urllib.request


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
    return html


def processDownload(f):
    print(f.result()[:25])


with concurrent.futures.ThreadPoolExecutor() as executor:
    f1 = executor.submit(download)
    f2 = executor.submit(download)
    f1.add_done_callback(processDownload)
    f2.add_done_callback(processDownload)
    print("waiting")

Page 200

import concurrent.futures
import urllib.request


def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
    return html


def processDownloadA(f):
    print(f.result()[:25])
    f2 = executor.submit(download)
    f2.add_done_callback(processDownloadB)


def processDownloadB(f):
    print(f.result()[:25])


with concurrent.futures.ThreadPoolExecutor() as executor:
    f1 = executor.submit(download)
    f1.add_done_callback(processDownloadA)

    print("waiting")
    while True:
        pass

Page 203-204

import concurrent.futures
import threading
import time
from cmath import sqrt

myCounter = 0
countlock = threading.Lock()


def count():
    global myCounter
    for i in range(100000):
        with countlock:
            temp = myCounter+1
            x = sqrt(2)
            myCounter = temp


with concurrent.futures.ThreadPoolExecutor() as execute:
    t1 = time.perf_counter()
    f1 = execute.submit(count)
    f2 = execute.submit(count)
    concurrent.futures.wait(
        [f1, f2], return_when=concurrent.futures.ALL_COMPLETED)
    t2 = time.perf_counter()
print((t2-t1)*1000)
print(myCounter)

Page 205

import concurrent.futures
import multiprocessing
import time
import ctypes


def counter():
    global count
    for i in range(10000):
        with count:
            temp = count.value+1
            count.value = temp


def setup(var):
    global count
    count = var


if __name__ == '__main__':
    myCounter = multiprocessing.Value(ctypes.c_int, 0)
    with concurrent.futures.ProcessPoolExecutor(2,
                                                initializer=setup, initargs=(myCounter,)) as execute:

        t1 = time.perf_counter()
        f1 = execute.submit(counter)
        f2 = execute.submit(counter)
        concurrent.futures.wait([f1, f2],
                                return_when=concurrent.futures.ALL_COMPLETED)
        t2 = time.perf_counter()
        print(myCounter.value)
    print((t2-t1)*1000)

Page 206

import concurrent.futures
import multiprocessing
import multiprocessing.managers
import time
import ctypes


def counter(count, lock):
    for i in range(10000):
        with lock:
            temp = count.value+1
            count.value = temp


if __name__ == '__main__':

    with multiprocessing.Manager() as man:
        with concurrent.futures.ProcessPoolExecutor(2) as execute:

            myCounter = man.Value(ctypes.c_int, 0)
            myLock = man.Lock()

            t1 = time.perf_counter()
            f1 = execute.submit(counter, myCounter, myLock)
            f2 = execute.submit(counter, myCounter, myLock)
            concurrent.futures.wait([f1, f2],
                                    return_when=concurrent.futures.ALL_COMPLETED)
            t2 = time.perf_counter()
            print(myCounter.value)
    print((t2-t1)*1000)

Page 207

import concurrent.futures
import time


def taskA():
    time.sleep(1)
    ans = f2.result()
    return ans


def taskB():
    time.sleep(1)
    ans = f1.result()
    return ans


with concurrent.futures.ThreadPoolExecutor(2) as execute:
    f1 = execute.submit(taskA)
    f2 = execute.submit(taskB)
    concurrent.futures.wait([f1, f2],
                            return_when=concurrent.futures.ALL_COMPLETED)
    print(f1.result())

Page 208

import concurrent.futures
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return pi*4


if __name__ == '__main__':
    N = 10000000
    with concurrent.futures.ProcessPoolExecutor(2) as execute:
        t1 = time.perf_counter()
        f1 = execute.submit(myPi, 1, N//2)
        f2 = execute.submit(myPi, N//2+1, N)
        PI = f1.result()
        PI += f2.result()
        t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(PI)

Page 216

import asyncio


async def test1(msg):
    print(msg)


async def main():
    await test1("Hello Coroutine World")

asyncio.run(main())

Page 219

import asyncio


async def count(n):
    for i in range(n):
        print(i)
    return n


async def main(myValue):
    t1 = asyncio.create_task(count(10))
    print("Hello Coroutine World")
    await asyncio.sleep(5)
    return myValue

result = asyncio.run(main(42))
print(result)

Page 221

import asyncio


async def test1(msg):
    print(msg)


async def main():
    asyncio.create_task(test1("one"))
    asyncio.create_task(test1("two"))

    await test1("three")
    print("Hello Coroutine World")
    await asyncio.sleep(0)

asyncio.run(main())

Page 225

import asyncio


async def test1(msg):
    print(msg)
    return msg


async def main():
    t1 = asyncio.create_task(test1("one"))
    t2 = asyncio.create_task(test1("two"))
    done, pending = await asyncio.wait([t1, t2],
                                       return_when=asyncio.ALL_COMPLETED)
    for t in done:
        print(t.result())
    print("Hello Coroutine World")
asyncio.run(main())

Page 226

import asyncio


async def test1(msg):
    print(msg)
    return msg


async def main():
    result = await asyncio.gather(test1("one"), test1("two"))
    print(result)
    print("Hello Coroutine World")

asyncio.run(main())

Page 227

import asyncio


async def test1(msg):
    try:
        await asyncio.sleep(0)
    except:
        pass
    print(msg)
    return msg


async def main():
    t1 = asyncio.create_task(test1("one"))
    await asyncio.sleep(0)
    t1.cancel()
    print("Hello Coroutine World")
    await asyncio.sleep(0)

asyncio.run(main())

Page 228 top

import asyncio


async def test(msg):
    print(msg)
    raise Exception("Test exception")


async def main():
    t1 = asyncio.create_task(test("one"))
    try:
        await t1
    except:
        print("an exception has occurred")
    print("Hello Coroutine World")
    await asyncio.sleep(0)

asyncio.run(main())

Page 228 bottom

import asyncio


async def test(msg):
    print(msg)
    raise Exception("Test exception")


async def main():
    t1 = asyncio.create_task(test("one"))

    done, pending = await asyncio.wait([t1])
    print(repr(done.pop().exception()))

    print("Hello Coroutine World")
    await asyncio.sleep(0)

asyncio.run(main())

Page 229

import asyncio


async def count():
    global myCounter
    for i in range(1000):
        temp = myCounter+1
        myCounter = temp


async def main():
    t1 = asyncio.create_task(count())
    t2 = asyncio.create_task(count())
    await asyncio.wait([t1, t2])
    print(myCounter)

myCounter = 0
asyncio.run(main())

Page 230

import asyncio
import asyncio.locks


async def count():
    global myCounter
    global myLock
    for i in range(1000):
        async with myLock:
            temp = myCounter+1
            await asyncio.sleep(0)
            myCounter = temp


async def main():
    t1 = asyncio.create_task(count())
    t2 = asyncio.create_task(count())
    await asyncio.wait([t1, t2])
    print(myCounter)

myCounter = 0
myLock = asyncio.locks.Lock()
asyncio.run(main())

Page 232

import asyncio
import random

idGlobal = 0


async def inner(idparam):
    global idGlobal
    await asyncio.sleep(0)
    if idparam != idGlobal:
        print("error")


async def outer():
    global idGlobal
    id = random.randint(0, 10000)
    idGlobal = id
    await inner(id)


async def main():
    await asyncio.gather(outer(), outer())

asyncio.run(main())

Page 233

import asyncio
import random
import contextvars

idGlobalCtx = contextvars.ContextVar("id")


async def inner(idparam):
    await asyncio.sleep(0)
    print(idparam, idGlobalCtx.get(), end=" ")
    if idparam != idGlobalCtx.get():
        print("error", end="")
    print()


async def outer():
    global idGlobal
    id = random.randint(0, 10000)
    idGlobalCtx.set(id)
    await inner(id)


async def main():
    await asyncio.gather(outer(), outer())

asyncio.run(main())

Page 234

import asyncio
import asyncio.queues


async def addCount(q):
    for i in range(1000):
        await q.put(i)


async def getCount(q, id):
    while True:
        i = await q.get()
        print(id, i)
        await asyncio.sleep(0)


async def main():
    q = asyncio.queues.Queue()
    t1 = asyncio.create_task(addCount(q))
    t2 = asyncio.create_task(getCount(q, "t2"))
    t3 = asyncio.create_task(getCount(q, "t3"))
    await asyncio.wait([t1, t2, t3])

asyncio.run(main())

Page 243

import asyncio
import urllib.parse
import time
import email


def parseHeaders(headers):
    message = email.message_from_string(headers)
    return dict(message.items())


async def download(url):
    url = urllib.parse.urlsplit(url)
    reader, writer = await asyncio.open_connection(
        url.hostname, 443, ssl=True)

    request = (
        f"GET /index.html HTTP/1.1\r\n"
        f"Host: {url.hostname}\r\n"
        f"\r\n"
    )
    writer.write(request.encode('ascii'))

    headers = ""
    line = await reader.readline()

    while True:
        line = await reader.readline()
        line = line.decode('ascii')
        if line == "\r\n":
            break
        headers += line

    headers = parseHeaders(headers)
    length = int(headers["Content-Length"])

    line = await reader.read(length)
    line = line.decode('utf8')
    writer.close()
    await writer.wait_closed()
    return line


async def main():
    start = time.perf_counter()
    results = await asyncio.gather(download('http://www.example.com/'), download('http://www.example.com/'))
    end = time.perf_counter()
    print((end-start)*1000)
    print(results[0][:25])
    print(results[1][:25])


asyncio.run(main())

Page 247

import asyncio
import email
import email.utils


async def handleRequest(reader, writer):
    headers = ""
    while True:
        line = await reader.readline()
        line = line.decode('ascii')
        if line == "\r\n":
            break
        headers += line
    print(headers)
    html = ("<html><head><title>Test Page</title></head><body>"
            "page content"
            "</p></body></html>\r\n")
    headers = ("HTTP/1.1 200 OK\r\n"
               "Content-Type: text/html; charset=UTF-8\r\n"
               "Server:PythonAcyncio\r\n"
               f"Date: {email.utils.formatdate(timeval=None,localtime=False, usegmt=True)}\r\n"
               f"Content-Length:{len(html)}\r\n\r\n"
               )
    data = headers.encode("ascii")+html.encode("utf8")
    writer.write(data)
    await writer.drain()
    await writer.wait_closed()


async def main():
    server = await asyncio.start_server(handleRequest, "", 8080)
    async with server:
        await server.serve_forever()


asyncio.run(main())

Page 250

import urllib.request
import asyncio
import time

async def download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
        return html

async def main():
    t1=time.perf_counter()
    results=await asyncio.gather(download(),download())
    t2=time.perf_counter()
    print((t2-t1)*1000)
    print(results[0][:25])

asyncio.run(main())

Page 251

import urllib.request
import asyncio
import time


def _download():
    with urllib.request.urlopen('http://www.example.com/') as f:
        html = f.read().decode('utf-8')
        return html


async def download():
    return await asyncio.to_thread(_download)


async def main():
    n = 1000
    t1 = time.perf_counter()
    results = await asyncio.gather(*[download() for i in range(n)])
    t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(results[0][:25])

asyncio.run(main())

Page 253

import asyncio
import time


async def tick():
    i = 0
    while True:
        i += 1
        print("TICK", i)
        await asyncio.sleep(0.5)


def _myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return 4*pi


async def myPi(m, n):
    return await asyncio.to_thread(_myPi, m, n)


async def main():
    n = 100
    t1 = time.perf_counter()
    T1 = asyncio.create_task(myPi(1, 10000000))
    T2 = asyncio.create_task(tick())
    done, pending = await asyncio.wait([T1, T2],
                                       return_when=asyncio.FIRST_COMPLETED)
    t2 = time.perf_counter()
    print((t2-t1)*1000)
    print(done.pop().result())

asyncio.run(main())

Page 255

import aiohttp
import asyncio


async def main():
    async with aiohttp.ClientSession() as session:
        async with session.get("http://www.example.com") as response:

            print("Status:", response.status)
            print("Content-type:", response.headers['content-type'])

            html = await response.text()
            print("Body:", html[:25], "...")

asyncio.run(main())

Page 256

import tkinter

count = 0
root = None
label1 = None


def stopProg(e):
    global root
    root.destroy()


def transfertext(e):
    global root, label1
    global count
    count = count+1
    label1.configure(text=count)


def runGUI():
    global root, label1
    root = tkinter.Tk()
    button1 = tkinter.Button(root, text="Exit")
    button1.pack()
    button1.bind('<Button-1>', stopProg)
    button2 = tkinter.Button(root, text="Click Me")
    button2.pack()
    button2.bind('<Button-1>', transfertext)
    label1 = tkinter.Label(root, text="nothing to say")
    label1.pack()
    root.mainloop()


runGUI()

Page 257

import asyncio
import tkinter

count = 0
root = None
label1 = None
T1 = None


def stopProg(e):
    global T1
    global root
    T1.cancel()
    root.quit()


def transfertext(e):
    global root, label1
    global count
    count = count+1
    label1.configure(text=count)


async def updater(interval):
    global root
    while True:
        root.update()
        await asyncio.sleep(interval)


def setupGUI():
    global root, label1
    root = tkinter.Tk()

    button1 = tkinter.Button(root, text="Exit")
    button1.pack()
    button1.bind('<Button-1>', stopProg)
    button2 = tkinter.Button(root, text="Click Me")
    button2.pack()
    button2.bind('<Button-1>', transfertext)
    label1 = tkinter.Label(root, text="nothing to say")
    label1.pack()


async def tick():
    i = 0
    while True:
        i += 1
        print("TICK", i)
        await asyncio.sleep(0.5)


async def main():
    global T1, root
    root.tk.willdispatch()
    T1 = asyncio.create_task(updater(0.01))
    T2 = asyncio.create_task(tick())
    await asyncio.wait((T1,))

setupGUI()
asyncio.run(main())

Page 259

import asyncio
import tkinter
import threading

count = 0
root = None
label1 = None


def stopProg(e):
    global root
    root.quit()


def transfertext(e):
    global label1
    global count
    count = count+1
    label1.configure(text=count)


def setupGUI():
    global root, label1
    root = tkinter.Tk()
    button1 = tkinter.Button(root, text="Exit")
    button1.pack()
    button1.bind('<Button-1>', stopProg)
    button2 = tkinter.Button(root, text="Click Me")
    button2.pack()
    button2.bind('<Button-1>', transfertext)
    label1 = tkinter.Label(root, text="nothing to say")
    label1.pack()


async def tick():
    i = 0
    while True:
        i += 1
        print("TICK", i)
        await asyncio.sleep(0.5)


def runasyncio():
    asyncio.run(main())


async def main():
    T2 = asyncio.create_task(tick())
    await asyncio.wait((T2,))

setupGUI()
t1 = threading.Thread(target=runasyncio, daemon=True)
t1.start()
root.mainloop()

Page 262

import asyncio


async def main():
    p = await asyncio.create_subprocess_exec("dir", "/",
                                             stdout=asyncio.subprocess.PIPE)
    stdout_data, stderr_data = await p.communicate()
    print(stdout_data)
    print("finished")

asyncio.run(main())

Page 263

import asyncio


async def main():
    p = await asyncio.create_subprocess_exec("./myscript.sh",
                                             stdout=asyncio.subprocess.PIPE, stdin=asyncio.subprocess.PIPE)
    ans = await p.stdout.readline()
    print("message", ans)
    p.stdin.write(b"mike\n")
    ans = await p.stdout.readline()
    print("message", ans)

asyncio.run(main())

Page 264

import asyncio

async def main():
    p = await asyncio.create_subprocess_exec("./myscript.sh",stdout=asyncio.subprocess.PIPE,stdin=asyncio.subprocess.PIPE)
    T=asyncio.create_task(p.stdout.read(100))
    try:
        done,pending=await asyncio.wait([T],timeout= 0.1)
    except asyncio.TimeoutError:
        pass
    print("message",T.result())
    p.stdin.write(b"mike\n")
    ans= await p.stdout.readline()
    print("message",ans)
    await p.wait()

asyncio.run(main())

Page 268

import asyncio


def myFunction(value):
    print(value)


myLoop = asyncio.new_event_loop()
myLoop.call_later(3, myFunction, 43)
t = myLoop.time()+2
myLoop.call_at(t, myFunction, 44)
myLoop.call_soon(myFunction, 42)

myLoop.call_soon(myFunction, 45)
myLoop.run_forever()

Page 269

import asyncio


async def myFunction1(value):
    await asyncio.sleep(0)
    print(value)


async def myFunction2(value):
    print(value)
    await asyncio.sleep(0)

myLoop = asyncio.new_event_loop()
T1 = myLoop.create_task(myFunction1(42))
T2 = myLoop.create_task(myFunction2(43))

myLoop.run_forever()

Page 271

import asyncio
import threading
import time


def myMakeTask(loop, cor, value):
    loop.call_soon_threadsafe(lambda: loop.create_task(cor(value)))


async def myFunction1(value):
    await asyncio.sleep(0)
    print(value)


async def myFunction2(value):
    print(value)
    await asyncio.sleep(0)

myLoop = None


def myThreadLoop():
    global myLoop
    myLoop = asyncio.new_event_loop()
    T1 = myLoop.create_task(myFunction1(42))
    T2 = myLoop.create_task(myFunction2(43))
    myLoop.run_forever()


t = threading.Thread(target=myThreadLoop)
t.start()
time.sleep(0)
while not myLoop:
    pass
myMakeTask(myLoop, myFunction1, 44)
t.join()

Page 272

import asyncio
import concurrent.futures


def myFunction1(value):
    print(value)
    return value


if __name__ == '__main__':
    pool = concurrent.futures.ProcessPoolExecutor()
    myLoop = asyncio.new_event_loop()

    T1 = myLoop.run_in_executor(pool, myFunction1, 42)
    T2 = myLoop.run_in_executor(pool, myFunction1, 43)

    myLoop.run_until_complete(asyncio.wait([T1, T2]))
    print(T1.result())
    print(T2.result())
    pool.shutdown()

Page 273

import asyncio
import concurrent.futures
import time


def myPi(m, n):
    pi = 0
    for k in range(m, n+1):
        s = 1 if k % 2 else -1
        pi += s / (2 * k - 1)
    return pi*4


if __name__ == '__main__':
    pool = concurrent.futures.ProcessPoolExecutor()

    myLoop = asyncio.new_event_loop()

    N = 10000000
    with concurrent.futures.ProcessPoolExecutor() as pool:
        t1 = time.perf_counter()
        T1 = myLoop.run_in_executor(pool, myPi, 1, N//2)
        T2 = myLoop.run_in_executor(pool, myPi, N//2+1, N)
        myLoop.run_until_complete(asyncio.wait([T1, T2]))
        t2 = time.perf_counter()

    PI = T1.result()
    PI += T2.result()
    print((t2-t1)*1000)
    print(PI)

Page 276

import asyncio


async def main():
    loop = asyncio.get_running_loop()
    transport, protocol = await loop.create_datagram_endpoint(
        lambda: asyncio.DatagramProtocol(),
        local_addr=("192.168.253.20", 8080))

    data = b"Hello UDP World"
    transport.sendto(data, addr=("192.168.253.14", 8080))
    transport.close()

asyncio.run(main())

Page 277

import asyncio


class ClientDatagramProtocol(asyncio.DatagramProtocol):
    def datagram_received(self, data, addr):
        message = data.decode("utf8")
        print("Received", message, "from", addr)


async def main():
    loop = asyncio.get_running_loop()
    transport, protocol = await loop.create_datagram_endpoint(
        lambda: ClientDatagramProtocol(),
        local_addr=('192.168.253.14', 8080))
    await asyncio.sleep(1000)
    transport.close()

asyncio.run(main())

Page 279

import asyncio


async def main():
    loop = asyncio.get_running_loop()
    transport, protocol = await loop.create_datagram_endpoint(
        lambda: asyncio.DatagramProtocol(),
        local_addr=("192.168.253.20", 8080), allow_broadcast=True)
    sock = transport.get_extra_info('socket')
    print(sock)
    data = b"Hello UDP World"
    await loop.sock_connect(sock, ("192.168.253.255", 8080))
    await loop.sock_sendall(sock, data)
    transport.close()

asyncio.run(main())

Page 280

import asyncio
import socket


async def main():
    loop = asyncio.get_running_loop()

    sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    sock.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)

    data = b"Hello UDP World"
    await loop.sock_connect(sock, ("192.168.253.255", 8080))
    await loop.sock_sendall(sock, data)

asyncio.run(main())

Programming the Raspberry Pi Pico/W in MicroPython

We have decided not to make the programs available as a download because this is not the point of the book - the programs are not finished production code but something you should type in and study.

The best solution is to provide the source code of the programs in a form that can be copied and pasted into Thonny or VS Code project. 

The only downside is that you have to create a project to paste the code into.

To do this follow the instructions in the book.

All of the programs below were copy and pasted from working programs in the IDE. They have been formatted using the built in formatter and hence are not identical in layout to the programs in the book. This is to make copy and pasting them easier. The programs in the book are formatted to be easy to read on the page.

If anything you consider important is missing or if you have any requests or comments  contact:

This email address is being protected from spambots. You need JavaScript enabled to view it. 

Page 32

from machine import Pin
import time

pin = Pin("LED", Pin.OUT)
while True:
    pin.value(1)
    time.sleep(1)
    pin.value(0)
    time.sleep(1)

Page 32

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    time.sleep(1)
    pin.value(0)
    time.sleep(1)

Page 38

from machine import Pin
import time

pin = Pin(22,Pin.OUT)
while True:
    pin.toggle()
    time.sleep(1)
 

Page 38

from machine import  Pin
def flash():
    pin = Pin(22, Pin.OUT)
    while True:
        pin.value(1)
        pin.value(0)
flash()

Page 39

from machine import Pin

@micropython.native
def flash():
    pin = Pin(22, Pin.OUT)
    while True:
        pin.value(1)
        pin.value(0)
flash()

Page 40

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    time.sleep(0.5)
    pin.value(0)
    time.sleep(0.5)
 

Page 40

from machine import Pin
import time

pin = Pin(22, Pin.OUT)
while True:
    pin.value(1)
    time.sleep_us(10)
    pin.value(0)
    time.sleep_us(10)

Page 40

from machine import Pin
import time
pin = Pin(22, Pin.OUT)
n = 10
while True:
    for i in range(n):
        pass
    pin.value(1)
    for i in range(n):
        pass
    pin.value(0)

Page 42

from machine import Pin

pin1 = Pin(21, Pin.OUT)
pin2 = Pin(22, Pin.OUT)
while True:
    pin1.value(1)
    pin2.value(0)
    pin1.value(0)
    pin2.value(1)

Page 44

from machine import Pin
import machine

def gpio_get():
    return machine.mem32[0xd0000000+0x010]

def gpio_set(value, mask):
    machine.mem32[0xd0000000 +  0x01C] = (machine.mem32[0xd0000000+0x010]) ^ value & mask

pin = Pin(22, Pin.OUT)
pin = Pin(21, Pin.OUT)
value1 = 1 << 22 | 0 << 21
value2 = 0 << 22 | 1 << 21
mask = 1 << 22 | 1 << 21
while True:
    gpio_set(value1, mask)
    gpio_set(value2, mask)
 

Page 65

from machine import Pin
import time
pinIn = Pin(22, Pin.IN,Pin.PULL_UP)
pinLED = Pin(25, Pin.OUT)

while True:
    if pinIn.value():
        pinLED.on()
    else:
        pinLED.off()
    time.sleep(0.5)

Page 66

from machine import Pin
import time
pinIn = Pin(22, Pin.IN, Pin.PULL_DOWN)
pinLED = Pin(25, Pin.OUT)

while True:
    while pinIn.value() == 0:
        pass
    while pinIn.value() == 1:
        pass
    pinLED.on()
    time.sleep(1)
    pinLED.off()

Page 67 

from machine import Pin
import time
pinIn = Pin(22, Pin.IN, Pin.PULL_DOWN)
pinLED = Pin(25, Pin.OUT)

while True:
    while pinIn.value() == 0:
        pass
    t = time.ticks_ms()
    time.sleep_ms(1)
    while pinIn.value() == 1:
        pass
    t = time.ticks_diff(time.ticks_ms(), t)
    if t < 2000:
        pinLED.on()
        time.sleep(1)
        pinLED.off()
    else:
        for i in range(10):
            pinLED.on()
            time.sleep_ms(100)
            pinLED.off()
            time.sleep_ms(100)

Page 68

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

while True:
    while pinIn.value() == 1:
        pass
    while pinIn.value() == 0:
        pass

    t = time.ticks_us()
    while pinIn.value() == 1:
        pass
    t = time.ticks_diff(time.ticks_us(), t)
    print(t)
    time.sleep(1)

Page 69

import time
import machine

pinIn = machine.Pin(22, machine.Pin.IN)

while True:
    t = machine.time_pulse_us(pinIn, 1)
    print(t)
    time.sleep(1)

Page 69

import machine
import time

import machine
pinIn = machine.Pin(22, machine.Pin.IN)

while True:
    while pinIn.value() == 1:
        pass
    t = machine.time_pulse_us(pinIn, 1)
    print(t)
    time.sleep(1)

Page 72

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

s = 0
count = 0
while True:
    i = pinIn.value()
    t = time.ticks_add(time.ticks_us(), 1000*100)
    if s == 0:  # button not pushed
        if i:
            s = 1
            count = count+1
            print("Button Push ", count)
    elif s == 1:  # button pushed
        if not i:
            s = 0
    else:
        s = 0
    while time.ticks_us() < t:
        pass

Page 74

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)

s = 0
while True:
    i = pinIn.value()
    t = time.ticks_add(time.ticks_us(), 1000*100)
    if s == 0:  # button not pushed
        if i:
            s = 1
        tpush = t
    elif s == 1:  # button pushed
        if not i:
            s = 0
            if time.ticks_diff(t, tpush) > 2000000:
                print("Button held \n\r")
            else:
                print("Button pushed \n\r")
    else:
        s = 0
    while time.ticks_us() < t:
        pass 
 

Page 75 

from machine import Pin
import time
pinIn = Pin(22, Pin.IN)
pinLED1 = Pin(21, Pin.OUT)
pinLED2 = Pin(20, Pin.OUT)
pinLED3 = Pin(19, Pin.OUT)
pinLED1.on()
pinLED2.off()
pinLED3.off()
s = 0
buttonState = pinIn.value()
while True:
    buttonNow = pinIn.value()
    edge = buttonState-buttonNow
    buttonState = buttonNow
    t = time.ticks_add(time.ticks_us(), 1000*100)
    if s == 0:
        if edge == 1:
            s = 1
            pinLED1.off()
            pinLED2.on()
            pinLED3.off()

    elif s == 1:
        if edge == 1:
            s = 2
            pinLED1.off()
            pinLED2.off()
            pinLED3.on()
    elif s == 2:
        if edge == 1:
            s = 0
            pinLED1.on()
            pinLED2.off()
            pinLED3.off()
    else:
        s = 0
    while time.ticks_us() < t:
        pass
 

Page 83

from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_UP)
while True:
    event = gpio_get_events(22)
    if(event & Pin.IRQ_FALLING):
        print("falling")
    if(event & Pin.IRQ_RISING):
        print("rising")
    gpio_clear_events(22, Pin.IRQ_FALLING | Pin.IRQ_RISING)
    sleep(0.5)

Page 83

from utime import sleep
from machine import Pin

pin = Pin(22, Pin.IN, Pin.PULL_DOWN)

print("Press Button")
sleep(10)
if pin.value():
    print("Button Pressed")
else:
    print("Button Not Pressed")

Page 84

from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)

print("Press Button")
gpio_clear_events(22, Pin.IRQ_FALLING)
sleep(10)
event = gpio_get_events(22)
gpio_clear_events(22, Pin.IRQ_FALLING)
if event & Pin.IRQ_FALLING:
    print("Button Pressed")
else:
    print("Button Not Pressed")

Page 85

import time
from utime import sleep
from machine import Pin
import machine


def gpio_get_events(pinNo):
    mask = 0xF << 4 * (pinNo % 8)
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    return (machine.mem32[intrAddr] & mask) >> (4 * (pinNo % 8))


def gpio_clear_events(pinNo, events):
    intrAddr = 0x40014000 + 0x0f0 + (pinNo // 8)*4
    machine.mem32[intrAddr] = events << (4 * (pinNo % 8))


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
while True:
    gpio_clear_events(22, Pin.IRQ_FALLING | Pin.IRQ_RISING)
    while not(gpio_get_events(22) & Pin.IRQ_RISING):
        pass
    t = time.ticks_us()
    while not(gpio_get_events(22) & Pin.IRQ_FALLING):
        pass
    t = time.ticks_diff(time.ticks_us(), t)
    print(t)
    sleep(1)

Page 88

import time
from machine import Pin
import machine
import array

count = 0
t = array.array('L', [0]*20)


def myHandler(pin):
    global t, count
    t[count] = time.ticks_us()
    count = count+1
    if count > 19:
        for i in range(1, 20):
            print(time.ticks_diff(t[i], t[i-1]))
        pin.irq(None, Pin.IRQ_RISING, hard=True)
        return


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
pin.irq(myHandler, Pin.IRQ_RISING, hard=False)

Page 90

import time
from machine import Pin


def myHandler(pin):
    print(time.ticks_us())


pin = Pin(22, Pin.IN, Pin.PULL_DOWN)
pin.irq(myHandler, Pin.IRQ_RISING, hard=True)
while True:
    print("doing something useful")

Page 96

from machine import Pin, PWM
pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))

pwm16.freq(250)

pwm16.duty_u16(65535//2)
pwm17.duty_u16(65535//4) 
 

Page 97

from machine import Pin, PWM
import machine


def pwm_set_phase(sliceNo, phase):
    Addr = 0x40050000 + 0x14*sliceNo
    if phase:
        machine.mem32[Addr] = machine.mem32[Addr] | 0x2
    else:
        machine.mem32[Addr] = machine.mem32[Addr] & 0xFFFFFFFD


pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))
pwm16.freq(250)
pwm_set_phase(0, True)
pwm16.duty_u16(65535//2)
pwm17.duty_u16(65535//4)

Page 98

from machine import Pin, PWM
def pwm_set_polarity(sliceNo, channel, invert):
    Addr = 0x40050000 + 0x14*sliceNo
    if invert:
        machine.mem32[Addr] = machine.mem32[Addr] | 0x1 << (2+channel)
    else:
        machine.mem32[Addr] = machine.mem32[Addr] & ~(0x1 << (2+channel))


pwm16 = PWM(Pin(16))
pwm17 = PWM(Pin(17))

pwm16.freq(250)
pwm_set_polarity(0, 1, True)
pwm16.duty_u16(65535//4)
pwm17.duty_u16(65535//4)

Page 99

from machine import Pin, PWM

pwm16 = PWM(Pin(16))

pwm16.freq(50)

pwm16.duty_u16(65535//2)
while True:
    pwm16.duty_u16(65535//2)
    pwm16.duty_u16(65535//4)

Page 101

from machine import Pin, PWM
import array
import machine
import math


def pwm_get_wrap(sliceNo):
    Addr = 0x40050000 + 0x10+0x14*sliceNo
    return (machine.mem32[Addr])


wave = array.array('H', [0]*256)
for i in range(256):
    wave[i] = int(65535//2 + (math.sin(i * 2.0 * 3.14159 / 256.0) * 65535//2))


pwm16 = PWM(Pin(16))
pwm16.freq(125000000//256)

print(pwm_get_wrap(0))
while(True):
    for i in range(256):
        pwm16.duty_u16(wave[i])

Page 103

from utime import sleep_ms
from machine import Pin, PWM

pwm25 = PWM(Pin(25))
pwm25.freq(2000)

while True:
    for d in range(0,65535,655):
        pwm25.duty_u16(d)
        sleep_ms(50)

Page 105

from utime import sleep_ms
from machine import Pin, PWM

pwm25 = PWM(Pin(25))
pwm25.freq(2000)

while True:
    for b in range(0,100):
        pwm25.duty_u16(int(65535*b*b*b/1000000))
        sleep_ms(50)

Page 115

from machine import Pin, PWM
from time import sleep

class Motor:
    def __init__(self, pinNo):
        self.gpio = pinNo
        self._on = False
        self.speed=0

        self.pwm1=PWM(Pin(pinNo))
        self.pwm1.freq(2000)
        self.pwm1.duty_u16(0)

    def setSpeed(self,s):
        self._on=True
        self.speed=s
        self.pwm1.duty_u16(int(65535*s/100))
    
    def off(self):
        self._on=False
        self.pwm1.duty_u16(0)
    
    def on(self):
        self._on=True
        self.pwm1.duty_u16(int(65535*self.speed/100))

motor=Motor(16)
motor.setSpeed(50)
sleep(1)
motor.off()
sleep(1)
motor.setSpeed(90)
sleep(1)
motor.off()

Page 120

from machine import Pin, PWM
from time import sleep

class Motor:
    def __init__(self, pinNo):
        self.gpio = pinNo
        self._on = False
        self.speed=0

        self.pwm1=PWM(Pin(pinNo))
        self.pwm1.freq(2000)
        self.pwm1.duty_u16(0)

    def setSpeed(self,s):
        self._on=True
        self.speed=s
        self.pwm1.duty_u16(int(65535*s/100))
    
    def off(self):
        self._on=False
        self.pwm1.duty_u16(0)
    
    def on(self):
        self._on=True
        self.pwm1.duty_u16(int(65535*self.speed/100))

class BiMotor(Motor):
    def __init__(self, pinNo):
        super().__init__(pinNo)
        self.forward=True
        self.pwm2=PWM(Pin(pinNo+1))
        self.pwm2.duty_u16(0)
    
    def setForward(self,forward):
        if self.forward==forward:
            return
        self.pwm1.duty_u16(0)
        self.pwm1,self.pwm2=self.pwm2,self.pwm1        
        self.forward=forward
        self.pwm1.duty_u16(int(65535*self.speed/100))

motor=BiMotor(16)
motor.setSpeed(50)
sleep(1)
motor.setForward(False)
sleep(1)
motor.setSpeed(90)
sleep(1)
motor.setForward(True)
motor.off()

Page 123

from machine import Pin, PWM
from time import sleep

class Servo:
    def __init__(self, pinNo):
        self.pwm = PWM(Pin(pinNo))
        self.pwm.freq(50)
        self.position = 65535*2.5/100

    def setPosition(self, p):
        self.position = p
        self.pwm.duty_u16(int(65535*p/1000 + 65535*2.5/100))

servo=Servo(16)
servo.setPosition(100.0)
sleep(1)
servo.setPosition(50.0)
sleep(1)
servo.setPosition(0)

Page 124-125

from machine import Pin, PWM
import machine
from time import sleep


class Servo:
    def __init__(self, pinNo):
        self.pwm = PWM(Pin(pinNo))
        self.pin = pinNo
        self.pwm.freq(50)
        self.position = 65535*2.5/100

    def setPosition(self, p):
        self.position = p
        self.pwm.duty_u16(int(65535*p/1000 + 65535*2.5/100))

    def getSlice(self):
        return (self.pin >> 1) & 0x07

    def getChannel(self):
        return self.pin & 1

    def setPolarity(self, invert):
        sliceNo = self.getSlice()
        channel = self.getChannel()
        Addr = 0x40050000 + 0x14*sliceNo
        if invert:
            machine.mem32[Addr] = machine.mem32[Addr] | 0x1 << (2+channel)
        else:
            machine.mem32[Addr] = machine.mem32[Addr] & ~(0x1 << (2+channel))


servo = Servo(16)
servo.setPolarity(True)
servo.setPosition(100.0)
sleep(1)
servo.setPosition(50.0)
sleep(1)
servo.setPosition(0)

Page 136

from utime import sleep_ms
from machine import Pin
import machine


class StepperBi4():
    def __init__(self, pinA):
        self.phase = 0
        self.pinA = pinA
        self.timer = None
        self.forward = True
        self.speed = 0

        self.gpios = tuple([Pin(pinA, Pin.OUT), Pin(
            pinA+1, Pin.OUT), Pin(pinA+2, Pin.OUT), Pin(pinA+3, Pin.OUT)])
        self.gpios[0].high()
        self.gpioMask = 0xF << self.pinA
        self.halfstepSeq = [0x1, 0x3, 0x2, 0x6, 0x4, 0xC, 0x8, 0x9]
#   [
#             [0,0,0,1],
#             [0,0,1,1],
#             [0,0,1,0],
#             [0,1,1,0],
#             [0,1,0,0],
#             [1,1,0,0],
#             [1,0,0,0],
#             [1,0,0,1]
#    ]

    def _gpio_set(self, value, mask):
        machine.mem32[0xd0000000 +
                      0x01C] = (machine.mem32[0xd0000000+0x010] ^ value) & mask

    def setPhase(self, phase):
        value = self.halfstepSeq[phase] << self.pinA
        self._gpio_set(value, self.gpioMask)
        self.phase = phase

    def stepForward(self):
        self.phase = (self.phase+1) % 8
        self.setPhase(self.phase)

    def stepReverse(self):
        self.phase = (self.phase-1) % 8
        self.setPhase(self.phase)

    def doRotate(self, timer):
        if self.forward:
            self.stepForward()
        else:
            self.stepReverse()

    def rotate(self, forward, speed):
        self.forward = forward
        self.speed = speed
        if speed == 0:
            self.timer.deinit()
            self.timer = None
            return
        if self.timer == None:
            self.timer = machine.Timer()
        self.timer.init(freq=speed, mode=machine.Timer.PERIODIC,
                        callback=self.doRotate)


step = StepperBi4(16)
step.setPhase(0)
while True:
    step.rotate(True, 100)
    sleep_ms(500)
    step.rotate(True, 0)
    sleep_ms(500)

Page 147

from machine import Pin, SPI

spi = SPI(0, sck=Pin(6), miso=Pin(4), mosi=Pin(7))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)

read = bytearray(3)
write = bytearray([0xAA, 0xAA, 0xAA])
spi.write_readinto(write, read)

print(read, write)
spi.deinit()

Page 152

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep

spi = SPI(0, sck=Pin(18), miso=Pin(16), mosi=Pin(19))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)

CS = Pin(17, Pin.OUT)
CS.high()
sleep_ms(1)

write = bytearray([0xD0])
CS.low()
spi.write(write)
read = spi.read(1)
CS.high()
print("Chip ID is", hex(read[0]))

CS.low()
write = bytearray([0xF2, 0x01])
spi.write(write)
write = bytearray([0xF4, 0x27])
spi.write(write)
CS.high()

CS.low()
write = bytearray([0xF7])
spi.write(write)
sleep_ms(10)
rBuff = spi.read(8)
CS.high()

pressure = (rBuff[0] << 12) | (rBuff[1] << 4) | (rBuff[2] >> 4)
temperature = (rBuff[3] << 12) | (rBuff[4] << 4) | (rBuff[5] >> 4)
humidity = rBuff[6] << 8 | rBuff[7]

print("Humidity = ", humidity)
print("Pressure = ", pressure)
print("Temp. = ", temperature)

Page 157

import machine
import utime
sensor_temp = machine.ADC(4)
conversion_factor = 3.3 / (65535)

while True:
    reading = sensor_temp.read_u16() * conversion_factor
    temperature = 27 - (reading - 0.706)/0.001721
    print(temperature)
    utime.sleep(2)

Page 163

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep

spi = SPI(0, sck=Pin(18), miso=Pin(16), mosi=Pin(19))
spi.init(baudrate=500_000, bits=8, polarity=0, phase=0, firstbit=SPI.MSB)
CS = Pin(17, Pin.OUT)
CS.high()
sleep_ms(1)
CS.low()
write = bytearray([0x01, 0x80, 0x00])
read = bytearray(3)
spi.write_readinto(write, read)
CS.high()
data = (read[1] & 0x03) << 8 | read[2]
volts = data * 3.3 / 1023.0
print(volts)
spi.deinit()

Page 163

from utime import sleep_ms
from machine import Pin, SPI
from time import sleep


class spiADC:
    def __init__(self, spi, sckNo, misoNo, mosiNo, CSNo):
        self.spi = SPI(spi, sck=Pin(sckNo), miso=Pin(misoNo), mosi=Pin(mosiNo))
        self.spi.init(baudrate=500_000, bits=8, polarity=0,
                      phase=0, firstbit=SPI.MSB)
        self.CS = Pin(CSNo, Pin.OUT)
        self.CS.high()
        sleep_ms(1)

    def read(self, chan):
        write = bytearray([0x01, (0x08 | chan) << 4, 0x00])
        self.CS.low()
        read = bytearray(3)
        self.spi.write_readinto(write, read)
        self.CS.high()
        data = (read[1] & 0x03) << 8 | read[2]
        volts = data * 3.3 / 1023.0
        return volts


adc = spiADC(0, 18, 16, 19, 17)
volts = adc.read(1)
print(volts)

Page 177

from machine import Pin,I2C

i2c0=I2C(0,scl=Pin(17),sda=Pin(16),freq=400000)

buf = bytearray([0xE7])
i2c0.writeto( 0x40, buf, True)
read= i2c0.readfrom(0x40, 1, True)
print("User Register =",read)

Page 179

from utime import sleep_ms
from machine import Pin, I2C
from time import sleep

i2c0 = I2C(0, scl=Pin(17), sda=Pin(16), freq=100*1000)

buf = bytearray([0xE3])
i2c0.writeto(0x40, buf, False)
read = i2c0.readfrom(0x40, 3, True)
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)

Page 183

from utime import sleep_ms
from machine import Pin, I2C
from time import sleep


def crcCheck(msb, lsb, check):
    data32 = (msb << 16) | (lsb << 8) | check
    divisor = 0x988000
    for i in range(16):
        if data32 & 1 << (23 - i):
            data32 ^= divisor
        divisor >>= 1
    return data32


i2c0 = I2C(0, scl=Pin(17), sda=Pin(16), freq=100*1000)

buf = bytearray([0xE3])
i2c0.writeto(0x40, buf, False)
read = i2c0.readfrom(0x40, 3, True)
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)

data16 = (msb << 8) | (lsb & 0xFC)
temp = (-46.85 + (175.72 * data16 / (1 << 16)))
print("Temperature C ", temp)
print("Checksum=", crcCheck(msb, lsb, check))

buf = bytearray([0xF5])
i2c0.writeto(0x40, buf, True)
read = bytearray(3)
while True:
    sleep_ms(1)
    try:
        i2c0.readfrom_into(0x40, read, True)
        break
    except:
        continue
msb = read[0]
lsb = read[1]
check = read[2]
print("msb lsb checksum =", msb, lsb, check)
data16 = (msb << 8) | (lsb & 0xFC)
hum = -6 + (125.0 * data16) / 65536
print("Humidity ", hum)
print("Checksum=", crcCheck(msb, lsb, check))

Page 192

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def blink():
    label("again")
    set(pins, 1)
    set(pins, 0)
    jmp("again")


sm = rp2.StateMachine(0, blink, freq=2000, set_base=Pin(16))
sm.active(1)

Page 195

import rp2
from machine import Pin

@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def blink():
    label("again")
    set(pins, 1)
    set(x,31)
    label("loop1")
    nop() [31]
    jmp(x_dec,"loop1")  
    set(pins, 0)  
    set(x,31)
    label("loop2")
    nop() [31]
    jmp(x_dec,"loop2") 
    jmp("again")  


sm = rp2.StateMachine(0, blink, freq=2000, set_base=Pin(16))
sm.active(1)

Page 196

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, )
def squarewave():
    pull(block)
    label("again")
    set(pins, 1)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pins, 0)
    mov(x, osr)
    label("loop2")
    jmp(x_dec, "loop2")
    jmp("again")


sm = rp2.StateMachine(0, squarewave, freq=2000, set_base=Pin(16))
sm.active(1)
sm.put(0xFFF)

Page 198

import rp2
from machine import Pin


@rp2.asm_pio(out_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW))
def output():
    pull(block)
    label("again")
    out(pins, 2)
    jmp("again")


sm = rp2.StateMachine(0, output, freq=2000, out_base=Pin(
    16), out_shiftdir=rp2.PIO.SHIFT_RIGHT)
sm.active(1)
sm.put(0xFEDCBA98)

Page 200

import rp2
from machine import Pin


@rp2.asm_pio(out_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW), autopull=True)
def output():
    label("again")
    out(pins, 2)
    jmp("again")


sm = rp2.StateMachine(0, output, freq=2000, out_base=Pin(
    16), out_shiftdir=rp2.PIO.SHIFT_RIGHT)
sm.active(1)
while True:
    sm.put(0xFEDCBA98)

Page 202

import rp2
from machine import Pin

@rp2.asm_pio(sideset_init=rp2.PIO.OUT_LOW)
def squarewave():
    label("again")    
    nop().side(1)
    jmp("again").side(0) 

sm = rp2.StateMachine(0, squarewave, freq=2000,sideset_base=Pin(16))
sm.active(1)

Page 202

import rp2
from machine import Pin


@rp2.asm_pio(sideset_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW))
def squarewave():
    label("again")
    nop().side(2)
    jmp("again").side(1)


sm = rp2.StateMachine(0, squarewave, freq=2000, sideset_base=Pin(16))
sm.active(1)

Page 204

import rp2
from machine import Pin


@rp2.asm_pio()
def light():
    label("again")
    in_(pins, 1)
    push(block)
    jmp("again")


LED = Pin(25, mode=Pin.OUT)
in1 = Pin(16, mode=Pin.IN)
sm = rp2.StateMachine(0, light, freq=2000, in_base=Pin(16))
sm.active(1)
while True:
    flag = sm.get()
    if (flag == 0):
        LED.value(0)
    else:
        LED.value(1)

Page 206

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW)
def squarewave():
    label("again")
    wait(0, pin, 0)
    wait(1, pin, 0)
    set(pins, 1)
    set(pins, 0)
    jmp("again")


in1 = Pin(16, mode=Pin.IN)
sm = rp2.StateMachine(0, squarewave, freq=2000,
                      in_base=Pin(16), set_base=Pin(17))
sm.active(1)
 
 

Page 215

import dht
from machine import Pin
import time

dht=dht.DHT22(Pin(22))
while True:
    dht.measure()
    temp=dht.temperature()
    print(temp)
    hum=dht.humidity()
    print(hum)
    time.sleep(1)

Page 218

from machine import Pin
from utime import sleep_ms, ticks_us


class DHT22():
    def __init__(self, gpio):
        self.pin = gpio
        self.pin = Pin(2, mode=Pin.OUT)
        self.pin.high()
        self.checksum = 0
        self.temperature = 0
        self.humidity = 0
        sleep_ms(1)

    def getReading(self):
        DHT = self.pin
        DHT.low()
        sleep_ms(1)
        DHT.init(mode=Pin.IN)
        for i in range(2):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass

        data = 0
        t1 = ticks_us()
        for i in range(32):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass
            t2 = ticks_us()
            data = data << 1
            data = data | ((t2 - t1) > 100)
            t1 = t2

        checksum = 0
        for i in range(8):
            while DHT.value() == 1:
                pass
            while DHT.value() == 0:
                pass
            t2 = ticks_us()
            checksum = checksum << 1
            checksum = checksum | ((t2 - t1) > 100)
            t1 = t2
        byte1 = (data >> 24 & 0xFF)
        byte2 = (data >> 16 & 0xFF)
        byte3 = (data >> 8 & 0xFF)
        byte4 = (data & 0xFF)
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)

Page 222

import rp2
from machine import Pin


@rp2.asm_pio(set_init=rp2.PIO.OUT_LOW, autopush=True, in_shiftdir=rp2.PIO.SHIFT_RIGHT)
def dht22():
    wrap_target()
    label("again")
    pull(block)
    set(pins, 0)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 0)

    wait(1, pin, 0)
    wait(0, pin, 0)
    wait(1, pin, 0)
    wait(0, pin, 0)

    set(y, 31)
    label("bits")
    wait(1, pin, 0)
    set(x, 0)
    label("loop2")
    jmp(x_dec, "continue")
    label("continue")
    jmp(pin, "loop2")
    in_(x, 4)
    jmp(y_dec, "bits")

    set(y, 7)
    label("check")
    wait(1, pin, 0)
    set(x, 0)
    label("loop3")
    jmp(x_dec, "continue2")
    label("continue2")
    jmp(pin, "loop3")
    in_(x, 4)
    jmp(y_dec, "check")
    wrap()


class DHT22():
    def __init__(self, gpio):
        self.sm = rp2.StateMachine(0, dht22, freq=976562, in_base=Pin(
            gpio), set_base=Pin(gpio), jmp_pin=Pin(gpio))
        self.sm.active(1)

    def getByte(self):
        count = self.sm.get()
        byte = 0
        for i in range(8):
            byte = byte << 1
            if ((count >> i * 4) & 0x0F) > 8:
                byte = byte | 1
        return byte

    def getReading(self):
        self.sm.put(1000)
        byte1 = self.getByte()
        print(byte1)
        byte2 = self.getByte()
        byte3 = self.getByte()
        print(hex(byte2))
        byte4 = self.getByte()
        checksum = self.getByte()
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)

Page 226

import rp2
from machine import Pin


@rp2.asm_pio(set_init=(rp2.PIO.OUT_LOW, rp2.PIO.OUT_LOW), autopush=True, in_shiftdir=rp2.PIO.SHIFT_LEFT)
def dht22():
    wrap_target()
    label("again")
    pull(block)
    set(pins, 0)
    mov(x, osr)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 0)

    wait(1, pin, 0)
    wait(0, pin, 0)
    wait(1, pin, 0)
    wait(0, pin, 0)

    set(y, 31)
    label("bits")
    wait(1, pin, 0)[25]
    in_(pins, 1)
    wait(0, pin, 0)
    jmp(y_dec, "bits")

    set(y, 7)
    label("check")
    wait(1, pin, 0)[25]
    set(pins, 2)
    set(pins, 0)
    in_(pins, 1)
    wait(0, pin, 0)
    jmp(y_dec, "check")
    push(block)
    wrap()


class DHT22():
    def __init__(self, gpio):
        self.sm = rp2.StateMachine(0, dht22, freq=490196, in_base=Pin(
            gpio), set_base=Pin(gpio), jmp_pin=Pin(gpio))
        self.sm.active(1)

    def getReading(self):
        self.sm.put(500)
        data = 0
        data = self.sm.get()
        byte1 = (data >> 24 & 0xFF)
        byte2 = (data >> 16 & 0xFF)
        byte3 = (data >> 8 & 0xFF)
        byte4 = (data & 0xFF)
        checksum = self.sm.get() & 0xFF
        self.checksum = (checksum == (byte1+byte2+byte3+byte4) & 0xFF)
        self.humidity = ((byte1 << 8) | byte2) / 10.0
        neg = byte3 & 0x80
        byte3 = byte3 & 0x7F
        self.temperature = (byte3 << 8 | byte4) / 10.0
        if neg > 0:
            self.temperature = -self.temperature


dht = DHT22(2)
dht.getReading()
print("Checksum", dht.checksum)
print("Humidity= ", dht.humidity)
print("Temperature=", dht.temperature)  
 

Page 248

from utime import sleep_ms, sleep_us
from machine import Pin
from time import sleep


class DS18B20:
    def __init__(self, pin):
        self.pin = Pin(pin, mode=Pin.IN)
        self.pin.high()

    def presence(self):
        self.pin.init(mode=Pin.OUT)
        self.pin.high()
        sleep_ms(1)
        self.pin.low()
        sleep_us(480)
        self.pin.init(mode=Pin.IN)
        sleep_us(70)
        b = self.pin.value()
        sleep_us(410)
        return b

    @micropython.native
    def writeBit(self, b):
        if b == 1:
            delay1 = 1
            delay2 = 30
        else:
            delay1 = 30
            delay2 = 0
        self.pin.low()
        for i in range(delay1):
            pass
        self.pin.high()
        for i in range(delay2):
            pass

    def writeByte(self, byte):
        self.pin.init(mode=Pin.OUT)
        for i in range(8):
            self.writeBit(byte & 1)
            byte = byte >> 1
        self.pin.init(mode=Pin.IN)

    @micropython.native
    def readBit(self):
        self.pin.init(mode=Pin.OUT)
        self.pin.low()
        self.pin.high()
        self.pin.init(mode=Pin.IN)
        b = self.pin.value()
        sleep_us(60)
        return b

    def readByte(self):
        byte = 0
        for i in range(8):
            byte = byte | self.readBit() << i
        return byte

    def convert(self):
        self.writeByte(0x44)
        for i in range(500):
            sleep_ms(10)
            if self.readBit() == 1:
                j = i
                break
        return j

    def crc8(self, data, len):
        crc = 0
        for i in range(len):
            databyte = data[i]
            for j in range(8):
                temp = (crc ^ databyte) & 0x01
                crc >>= 1
                if temp:
                    crc ^= 0x8C
                databyte >>= 1
        return crc

    def getTemp(self):
        if self.presence() == 1:
            return -1000
        self.writeByte(0xCC)
        if self.convert() == 500:
            return -3000
        self.presence()
        self.writeByte(0xCC)
        self.writeByte(0xBE)
        data = []
        for i in range(9):
            data.append(self.readByte())
        if self.crc8(data, 9) != 0:
            return -2000
        t1 = data[0]
        t2 = data[1]
        temp1 = (t2 << 8 | t1)
        if t2 & 0x80:
            temp1 = temp1 | 0xFFFF0000
        return temp1/16


dS18B20 = DS18B20(2)
if dS18B20.presence() == 1:
    print("No device")
else:
    print("Device present")

print(dS18B20.getTemp())

Page 250

from utime import sleep_ms
from machine import Pin
import onewire

class DS18B20:
    def __init__(self,pin):
        self.ow=onewire.OneWire(Pin(pin))    
       
    def convert(self):
        self.ow.writebyte(0x44)
        for i in range(500):
            sleep_ms(10)
            if self.ow.readbit() == 1:
                j=i
                break
        return j
   
    def getTemp(self):
        if not self.ow.reset:
            return -1000
        self.ow.writebyte(0xCC)
        if self.convert()==500:
            return -3000
        self.ow.reset()
        self.ow.writebyte( 0xCC)
        self.ow.writebyte( 0xBE)
        data=bytearray(9)
        self.ow.readinto(data)
        if self.ow.crc8(data)!=0:
            return -2000
        t1 = data[0]
        t2 = data[1]
        temp1 = (t2 << 8 | t1)
        if t2 & 0x80:
            temp1=temp1 | 0xFFFF0000
        return temp1/16

dS18B20=DS18B20(22)
print(dS18B20.getTemp())

Page 257

import rp2
from machine import Pin
from utime import sleep_ms


@rp2.asm_pio(set_init=rp2.PIO.OUT_HIGH, out_init=rp2.PIO.OUT_HIGH, autopush=True, push_thresh=8)
def DS1820():
    wrap_target()
    label("again")
    pull(block)
    mov(x, osr)
    jmp(not_x, "read")
    label("write")
    set(pindirs, 1)
    set(pins, 0)
    label("loop1")
    jmp(x_dec, "loop1")
    set(pindirs, 2)[31]
    wait(1, pin, 0)[31]

    pull(block)
    mov(x, osr)
    label("bytes1")
    pull(block)
    set(y, 7)
    set(pindirs, 3)
    label("bit1")
    set(pins, 0)[1]
    out(pins, 1)[31]
    set(pins, 1)[20]
    jmp(y_dec, "bit1")
    jmp(x_dec, "bytes1")
    set(pindirs, 0)[31]
    jmp("again")

    label("read")
    pull(block)
    mov(x, osr)
    label("bytes2")
    set(y, 7)
    label("bit2")
    set(pindirs, 1)
    set(pins, 0)[1]
    set(pindirs, 0)[5]
    in_(pins, 1)[10]
    jmp(y_dec, "bit2")
    jmp(x_dec, "bytes2")
    wrap()


class DS18B20:
    def __init__(self, pin):
        self.sm = rp2.StateMachine(0, DS1820, freq=490196, set_base=Pin(2), out_base=Pin(
            2), in_base=Pin(2), out_shiftdir=rp2.PIO.SHIFT_RIGHT, in_shiftdir=rp2.PIO.SHIFT_RIGHT)
        self.sm.active(1)

    def writeBytes(self, bytes, len):
        self.sm.put(250)
        self.sm.put(len-1)
        for i in range(len):
            self.sm.put(bytes[i])

    def readBytes(self, len):
        self.sm.put(0)
        self.sm.put(len-1)
        bytes = []
        for i in range(len):
            bytes.append(self.sm.get() >> 24)
        return bytes

    def getTemp(self):
        self.writeBytes([0xCC, 0x44], 2)
        sleep_ms(1000)
        self.writeBytes([0xCC, 0xBE], 2)
        data = self.readBytes(9)
        t1 = data[0]
        t2 = data[1]
        temp1 = (t2 << 8 | t1)
        if t2 & 0x80:
            temp1 = temp1 | 0xFFFF0000
        return temp1/16


dS18B20 = DS18B20(2)
print(dS18B20.getTemp())

Page 267

from machine import UART, Pin
from utime import sleep_ms

uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("Hello World \n", "utf-8")
uart.write(SendData)
RecData = uart.read()
print(RecData)

Page 268

from machine import UART, Pin
from utime import sleep_ms

uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("A"*32, "utf-8")
uart.write(SendData)
sleep_ms(500)
RecData = uart.read(32)
print(RecData)

Page 266

from machine import UART, Pin, mem32
from utime import sleep_ms


def uart_read(uart):
    rxData = bytes()
    while uart.any() > 0:
        rxData += uart.read(1)
    return rxData


uart = UART(1, baudrate=9600, bits=8, parity=2, rx=Pin(5), tx=Pin(4))
SendData = bytearray("A"*65, "utf-8")
uart.write(SendData)
sleep_ms(500)
RecData = uart_read(uart)
print(RecData)
print(len(RecData))

Page 278

def setup(country, ssid, key):
    rp2.country(country)
    wifi=network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED=Pin("LED", Pin.OUT)
    LED.high()
    timeout=20000
    wifi.connect(ssid,key)
    timer=Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    s=0
    while timeout>0:
        s=wifi.status()
        if s==3 or s<0:
            break
        sleep_ms(100)
        timeout=timeout-100
   
    if(s<2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi

Page 280

wifi=network.WLAN(network.STA_IF)
wifi.active(True)
wifi.disconnect()
aps=wifi.scan()
for ap in aps:
    print(ap)

Page 282

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO


class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):

    def sendResponse(self, cmd):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)
        self.send_response(200)
        self.end_headers()
        response = BytesIO()
        response.write(b'This is a '+bytes(cmd, 'utf-8')+
                                               b' request. ')
        response.write(b'Received: ')
        response.write(body)
        self.wfile.write(response.getvalue())

    def do_GET(self):
        self.send_response(200)
        self.end_headers()
        self.wfile.write(b'Hello, world!')


    def do_HEAD(self):
        self.send_response(200)
        self.end_headers()

    def do_POST(self):
        self.sendResponse("POST")

    def do_PUT(self):
        self.sendResponse("PUT")

    def do_DELETE(self):
        self.sendResponse("DELETE")

    def do_PATCH(self):
        self.sendResponse("PATCH")


httpd = HTTPServer(('', 8080), SimpleHTTPRequestHandler)
httpd.serve_forever()

Page 285

import urequests
import network
import rp2
from machine import Pin, Timer
from time import sleep_ms

def setup(country, ssid, key):
    rp2.country(country)
    wifi = network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED = Pin("LED", Pin.OUT)
    LED.high()
    timeout = 20000
    wifi.connect(ssid, key)
    timer = Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
               callback=lambda t: LED.toggle())
    s = 0
    while timeout > 0:
        s = wifi.status()
        if s == 3 or s < 0:
            break
        sleep_ms(100)
        timeout = timeout-100

    if(s < 2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                   callback=lambda t: LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi


wifi = setup("country", "ssid", "key")

url = "http://192.168.253.45:8080"
r = urequests.get(url)
print(r.content)
r.close()

buf = b'Hello World'
r = urequests.post(url, data=buf)
print(r.content)
r.close()

r = urequests.put(url, data=buf)
print(r.content)
r.close()

r = urequests.patch(url, data=buf)
print(r.content)
r.close()

r = urequests.head(url)
print(r.content)
print(r.headers)
r.close()

r = urequests.delete(url, data=buf)
print(r.content)
r.close()

Page 287

from machine import Pin, Timer
import network
import rp2
import onewire
import ds18x20
from time import sleep_ms
import urequests

def setup(country, ssid, key):
    rp2.country(country)
    wifi = network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED = Pin("LED", Pin.OUT)
    LED.high()
    timeout = 20000
    wifi.connect(ssid, key)
    timer = Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
               callback=lambda t: LED.toggle())
    s = 0
    while timeout > 0:
        s = wifi.status()
        if s == 3 or s < 0:
            break
        sleep_ms(100)
        timeout = timeout-100

    if(s < 2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                   callback=lambda t: LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi



wifi = setup("country", "ssid", "key")
url = "http://192.168.253.45:8080"

ow = onewire.OneWire(Pin(22))
presence = ow.reset()
if presence:
    print("Device present")
else:
    print("No device")

DS = ds18x20.DS18X20(ow)
roms = DS.scan()

while True:
    DS.convert_temp()
    temp = DS.read_temp(roms[0])
    buf = str(temp).encode("utf-8")
    try:
        r = urequests.put(url, data=buf)
        r.close()
    except:
        print("Server Not Online")
    sleep_ms(500)

Page 288

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO

class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):
     
    def log_message(self,*args, **kwargs):
        pass

    def do_PUT(self):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)
        bodyString= body.decode(encoding="utf-8")
        temp=float(bodyString)
        print(temp)
        self.send_response(200)
        self.end_headers()

httpd = HTTPServer(('', 8080), SimpleHTTPRequestHandler)
httpd.serve_forever()

Page 294

import network
import socket
import rp2
from machine import Pin, Timer
from time import sleep_ms

def setup(country, ssid, key):
    rp2.country(country)
    wifi = network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED = Pin("LED", Pin.OUT)
    LED.high()
    timeout = 20000
    wifi.connect(ssid, key)
    timer = Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
               callback=lambda t: LED.toggle())
    s = 0
    while timeout > 0:
        s = wifi.status()
        if s == 3 or s < 0:
            break
        sleep_ms(100)
        timeout = timeout-100

    if(s < 2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                   callback=lambda t: LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi



wifi = setup("country", "ssid", "key")

ai = socket.getaddrinfo("www.example.com", 80,socket.AF_INET)
addr = ai[0][-1]
s = socket.socket(socket.AF_INET)
s.connect(addr)

request = b"GET /index.html HTTP/1.1\r\nHost:example.org\r\n\r\n"
s.send(request)
print(s.recv(512))

Page 296

import network
import socket
import rp2
from machine import Pin, Timer
import ssl
from time import sleep_ms

def setup(country, ssid, key):
rp2.country(country)
wifi = network.WLAN(network.STA_IF)
wifi.active(True)
wifi.disconnect()
LED = Pin("LED", Pin.OUT)
LED.high()
timeout = 20000
wifi.connect(ssid, key)
timer = Timer()
timer.init(period=200, mode=Timer.PERIODIC,
callback=lambda t: LED.toggle())
s = 0
while timeout > 0:
s = wifi.status()
if s == 3 or s < 0:
break
sleep_ms(100)
timeout = timeout-100

if(s < 2):
timer.init(period=1000, mode=Timer.PERIODIC,
callback=lambda t: LED.toggle())
else:
timer.deinit()
LED.high()
return wifi

 

wifi = setup("country", "ssid", "key")

ai = socket.getaddrinfo("example.com", 443,socket.AF_INET)
addr = ai[0][-1]
s = socket.socket(socket.AF_INET)
s.connect(addr)
sslSock=ssl.wrap_socket(s)
request = b"GET / HTTP/1.1\r\nHost:example.com\r\n\r\n"
sslSock.write(request)
print(sslSock.read(1024))

Page 299-300

import network
import socket
import rp2
from time import sleep_ms
from machine import Pin, Timer
import onewire
import ds18x20

def setup(country, ssid, key):
    rp2.country(country)
    wifi = network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED = Pin("LED", Pin.OUT)
    LED.high()
    timeout = 20000
    wifi.connect(ssid, key)
    timer = Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
               callback=lambda t: LED.toggle())
    s = 0
    while timeout > 0:
        s = wifi.status()
        if s == 3 or s < 0:
            break
        sleep_ms(100)
        timeout = timeout-100

    if(s < 2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                   callback=lambda t: LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi
 
wifi = setup("country", "ssid", "key")
print("connected")
print(wifi.ifconfig())

ow = onewire.OneWire(Pin(22))
presence = ow.reset()
if presence:
    print("Device present")
else:
    print("No device")

DS = ds18x20.DS18X20(ow)
roms = DS.scan()

template = """<!DOCTYPE html>
<html>
<head> <title>Temperature</title> </head>
<body> <h1>Current Temperature</h1>
Hello Pico W Server World <br/>
The Temperature is: <!--#temp--><br/>
</body>
</html>
"""

addr = socket.getaddrinfo('0.0.0.0', 80)[0][-1]

s = socket.socket()
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.bind(addr)
s.listen(0)
while True:
    cl, addr = s.accept()
    print('client connected from', addr)
    print(cl.recv(512))

    DS.convert_temp()
    temp = DS.read_temp(roms[0])
    html=template.replace("<!--#temp-->",str(temp))
    headers = ("HTTP/1.1 200 OK\r\n"
            "Content-Type: text/html; charset=UTF-8\r\n"
            "Server:Pico\r\n"
            f"Content-Length:{len(html)}\r\n\r\n"
            )
    buf = headers.encode("utf-8")+html.encode("utf-8")
   
    cl.send(buf)
   
    cl.close()
s.close()

Page 303

import network
import socket
import rp2
from time import sleep_ms
from machine import Pin, Timer
import onewire
import ds18x20

import ssl



def setup(country, ssid, key):
    rp2.country(country)
    wifi=network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED=Pin("LED", Pin.OUT)
    LED.high()
    timeout=20000
    wifi.connect(ssid,key)
    timer=Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    s=0
    while timeout>0:
        s=wifi.status()
        if s==3 or s<0:
            break
        sleep_ms(100)
        timeout=timeout-100
   
    if(s<2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi




key=b'0\x82\x04\xbf\x02\x01\x000\r\x06\t*\x86H\x86\xf7\r\x01\x01\x01\x05\x00\x04\x82\x04\xa90\x82\x04\xa5\x02\x01\x00\x02\x82\x01\x01\x00\xb9SU\x05\x056\x8c\x92I\\?\xe5rb\x14\xaceG\xb8\x04n\x8f\xb6O\x04o\x9a\xcdP\xbe\xc3\xfb\x07\x8fl\xe4E\xd6\xf6>\xeb\\\xff\x9f\xbe\xad\x941\xda=\x9f\xca\x19\xa8iL\xa8\x91\xd8\xad\xafm\xb7\\|\xd8\x82\xa05:Oe\xe6\xe5\x18\xa6\x0f.\xea\x10<\xe6qh\x00?K\x12m)\xea\x08)\x9e>\'\xab\xca_\xddH\xa3\xd08\xe5\xec0+RB\xae\x8bR\'S\x8dq\x86\xc9\xa9{\xbd1W\xcbG\xb8\xe7V\xbc\x12\x077\x93\xab\xa1\xd6\xb1o\xc1\xdf\x0b\x0b\xa1\xf4Vm\x18\x8b\xf3\xf2\x9c\x86\xa1o\x92|Y\t\x85\x08UpnIFi3\x1d\xd4\x12\x863\n\xef\xb0\xa3\xbf\xd4\xf6\x1c7\x993\xe4\xf4$\x17\xe8\xb7\xb8k\xaaV\xeeB\x92\xa6*\xd9\xa9Y\x88P\x00I\x93Z4)\xb5\xfaW\xe6b\x04L\xee\xe9\xa4\xb1\xbf\'@s\xd0\xb3}\xc3\xf1[\t\xd9\x91\xeau\x0b\xd2\xba\x94\x7f\xbdO\x11\\e\x81Ed\x88\x97Z\x1a~\x16!\x02\x03\x01\x00\x01\x02\x82\x01\x01\x00\x81\xd9\x88\x85\x86\xfc\x8c\x8b\xe7\x08\xd2\xe0R?\xb4\x9a\x8209\x18)\xdbY\xf2\x8dz!-\xe0xyZ\xc7\x16PF\xb5D\x83\xae\xdc<\x82\x03\x0c\x98\x14p\xc5\xa8M\xf0M\xff\xf9\x1f\xb40\xd4p\x05\xad\xcb>\xeb^\xccO\xb2[\xd3\xcb\xe3v\xfb\xc9Ft)\x9e\x0c\xfd\xad\xd2\x1f\xf29\x08\x85"L\x0fB\x11\xd5\x1c\xf8\xbaHg\x04\x81z\xe0\x93\x00\xe5SED\xe1\x85N\x9f\xadd:z%\x8c1\xde\x02\xd7\xaf\xdf\xe6\x06F\xf6\xdc\x03\xf2K\x19B \x8eX\x9dx\xbb\x9c\xbcE\xa8:\x0f\xab\x0b\xd7\x8f\x7fV\xb1\x0c\xe4\x83\xfc\xcd\x9c\x1c\x072\x0e#\xc2\xb22o94r\xf6kp+\xd9\xcc/\x80\x11\xaa\xeb\xea\xac\'\xba\xecm\xe3;\xbf\xee{\xf7\x07K#\xe7\xc5\xadQ3\x9a[^\xf8\xe5\xb4}\xdc4\xedrD\x01\xef\x8ek\x100B\x03t6^\x87\\\x9c\xf9\x98\tN\xb9\xd9\x9a\xf1\xd3,o\xf5\xf3>\x9f8\xb7\x1f\x1a%\r\x8d\x9a\xd4S\x01\x02\x81\x81\x00\xee\xa5h5)w\xba,\x83\xad!\xa5\x7fzg\xa8v\x97F\xe0\x9a\x18\xe3\xc01\xb4\xd2\x96\x1a;\x94>\x99\xd9\xad\xcd<\xee\xf1\x9e\x041\x06\x9a\x8f\x82\xa4&z\xe0;[8{\xecu"\xa3\xeav&\x1e\xf6\xc2<F^\x19\x91\xa7\x05\x80=u\xe4\xf6c\xeb\x99\xcb\xb6\\\xcb\x88\x96]\x07\xf2\xef\xa8\x80\x0e\x9dh`\x19\xa5+\x03\xd3<\x06\xf4\x81\x96\x18\xe0>i\xbe:\xcc\xb9\x0cY\xfa\x03\x18\x11\'\x10\xa66\xb7-\xfdOq\x02\x81\x81\x00\xc6\xcdQ}\xa2\xdf\x84\x95\n\xac+\x1fx\x98\xb02\x19\x10yP\xa4<\xba\xb1F\xbc\x18\xdc \xe7\x91k\x8ed1a\xdb\xe1\x01\x0e\xb3\xba\x7fF{\xa9\x15\xcfN!\xaeBE\xe2\xdfv\xab\xa7\xf2/\xf7\x9cZ\xb1f\xbc\xe0z\x11\xab\xaf\xc0\x01 v_\x01\x1b\xac\xb8Q.h\xaa1yXF\x95\x1fb\x9e\x9c\x87\x9a[\x98\x90\x96\x0c\xe3\xf5#\nu8\\\xf0\x82\xf0\xec\x97\xa9\xb0\x10q\xd8\x84o\x0b#\r<\x05\x81J9\xb1\x02\x81\x80jA\x83\x90\x88\x12"\xf6\xc6\xfaCL\xe8\xe1\x9b]\xca\xcf\xb8c0\xb9|N\x8a\xd34 Y5\xc5\xdf\xc9\xa8\xbeU\xef\x97\x84E\x13 \xb1\x0c\x08q\xe6\x9c\xab\x81ClnM\xdf\x0e\x98\x89\xdbO\x17\xd2\x19\x94\x8a9\xda\x94\x0f\xe2\t\xf4\xfbh\x8e\xb5\x95\xef\xc4\xde\x8b\'\xee\x07\xb6\xcb]J\xb1\xa2\x98\xc1\xe9\x1c\x1c\r\xcf\x18\xc3\xef=~\xebF\xf7\x89\xc3\xee\x86.\x89\x07\xb6,\xe5\xb3\x07\xc5\xa3}}PDts)\xa2A\x02\x81\x81\x00\xac#^[\x86+:\x96\xff-\xc3\r6\x14(\x04\xc9\x15-\xa6x\xff\xa8\xbc\x15\xbe\x8b\\\x18\x15\xcb"1\xa2i\xec\rC\x0f\xf2V\x07\xb7k%jl[\x1b\x91(]t<\x158\xa1<\x04\x06*\xc64\xf5\x85;(\xb8*\x12\xdaTK\xe5z\xf9\x9aq\x07&v\x0c\xd4N\x02\x16\xcb,\x1a\xb5\x99d3\xafk%\xc2\xbd\xf7_d\x07\x7f\xf6\xef7\x05\xaa\xb0\x06\xc3&3\xa5#( \xcd\xd3\x84\xf6-\xe0y\xf7\xd0x\x91\x02\x81\x81\x00\x9fn\xb6|\xbf\x8bu\x98\xf0\xc3\xc2k\x1cn\x18y3\x88\xc8\x07l+\xc5\xbf\xd0\x1f\xa8\xe2e\xc6=\xb8\x1a\xfdW\x929;\xfc5~\x96\xb3\x9e\xa5A\xe3\x94\x8d\xc1I\x91\x87\xe0\xcd\x9bO\x80Z\xdcf\x157\xd0\x96:\x16\xb4%\xce\xd9\x17\xfa\xbeF\x19\x81\xc9\x96\xc2\xfd\x84\xafF\x87"\x91\xfb<\xd0\xc8\x11\xadJb\xf1\x17q\xeb\xb0\x11\xc3W\xc7\xf5\xe1\xa1B\x89\x8bZ\xc6\xe7\xa2\xf4?w\xa4\x0c\n\x89\xfd\x00S4\xabp\xd1'
 
cert=b'0\x82\x03k0\x82\x02S\xa0\x03\x02\x01\x02\x02\x14b\x01\xd9E\xad\x0e\xb3\x7f\x14\xc1\x83\x029V4|\x82E2U0\r\x06\t*\x86H\x86\xf7\r\x01\x01\x0b\x05\x000E1\x0b0\t\x06\x03U\x04\x06\x13\x02AU1\x130\x11\x06\x03U\x04\x08\x0c\nSome-State1!0\x1f\x06\x03U\x04\n\x0c\x18Internet Widgits Pty Ltd0\x1e\x17\r221219141736Z\x17\r231219141736Z0E1\x0b0\t\x06\x03U\x04\x06\x13\x02AU1\x130\x11\x06\x03U\x04\x08\x0c\nSome-State1!0\x1f\x06\x03U\x04\n\x0c\x18Internet Widgits Pty Ltd0\x82\x01"0\r\x06\t*\x86H\x86\xf7\r\x01\x01\x01\x05\x00\x03\x82\x01\x0f\x000\x82\x01\n\x02\x82\x01\x01\x00\xb9SU\x05\x056\x8c\x92I\\?\xe5rb\x14\xaceG\xb8\x04n\x8f\xb6O\x04o\x9a\xcdP\xbe\xc3\xfb\x07\x8fl\xe4E\xd6\xf6>\xeb\\\xff\x9f\xbe\xad\x941\xda=\x9f\xca\x19\xa8iL\xa8\x91\xd8\xad\xafm\xb7\\|\xd8\x82\xa05:Oe\xe6\xe5\x18\xa6\x0f.\xea\x10<\xe6qh\x00?K\x12m)\xea\x08)\x9e>\'\xab\xca_\xddH\xa3\xd08\xe5\xec0+RB\xae\x8bR\'S\x8dq\x86\xc9\xa9{\xbd1W\xcbG\xb8\xe7V\xbc\x12\x077\x93\xab\xa1\xd6\xb1o\xc1\xdf\x0b\x0b\xa1\xf4Vm\x18\x8b\xf3\xf2\x9c\x86\xa1o\x92|Y\t\x85\x08UpnIFi3\x1d\xd4\x12\x863\n\xef\xb0\xa3\xbf\xd4\xf6\x1c7\x993\xe4\xf4$\x17\xe8\xb7\xb8k\xaaV\xeeB\x92\xa6*\xd9\xa9Y\x88P\x00I\x93Z4)\xb5\xfaW\xe6b\x04L\xee\xe9\xa4\xb1\xbf\'@s\xd0\xb3}\xc3\xf1[\t\xd9\x91\xeau\x0b\xd2\xba\x94\x7f\xbdO\x11\\e\x81Ed\x88\x97Z\x1a~\x16!\x02\x03\x01\x00\x01\xa3S0Q0\x1d\x06\x03U\x1d\x0e\x04\x16\x04\x14\xcf\x1e\x1ce\xccs,\xd7b^\xd3\x99n\xa4\xebi\xe7\xe3\xe9S0\x1f\x06\x03U\x1d#\x04\x180\x16\x80\x14\xcf\x1e\x1ce\xccs,\xd7b^\xd3\x99n\xa4\xebi\xe7\xe3\xe9S0\x0f\x06\x03U\x1d\x13\x01\x01\xff\x04\x050\x03\x01\x01\xff0\r\x06\t*\x86H\x86\xf7\r\x01\x01\x0b\x05\x00\x03\x82\x01\x01\x00\x1c\x1d\x88\xca\xbd/5\xdf\x1b\xdb\xfe\xe4\x92\x7f\x98AK\xe37\x18qE\xf9\xc7D\x9ex\xb2Fo\xc3w\x17V\xe5fD1\x88\x7f\xe5\xfe\xd5}x\x10i\x9ah\xccl-*/\xfaa\x99\xc0\x82\xec\xbe\xca\'\x91v<\x1e g\xc3mm\xfe\x0f\xf7\xc5\xa8\xc8\xe0E\xce\xbb\\\x87s\x1d\x92b\xdd\x11\x12\x99\x196\x81\xf1\x15F\xf7i\xa7\xa2\x9b\xe6yG\x0e\xd73\x82\x13\x14\x95\xa4f-X\xcf\xb2\xcd\xb9AY=\xce\xb4 X\xe7o\xf5\x83\xad\xb5{y\xb4\x84\xd1\xa8\x0f\xcc;\x19\xd2\xd8A:\x1f\xd3\xc20\xb5\x12\'\xa0\xf0y\x8fE\x97\x0b\xbaj\x1c\xc6+\xfd\t$,\x05 B\x98C\x14j\xa2v6/q\xe8\x1bC\xd2w\xd7Z\xbeG\xd23",`\x00P\xb8a/\xea\xc5/\xc6Gh\xbe\x1e5\n`\x97g\t\xe6\xee\xfd\x88x\xfb\xeb\xe5\xb1\xd3\x96\x896*LE\xb7q\xe9\xf6\x07v\xac~\'s=\xe5\xa1N\x00f\x85!\x0e\xddt*\x98\x8a'
wifi = setup("country", "ssid", "key")
print(wifi.ifconfig())

ow = onewire.OneWire(Pin(22))
presence = ow.reset()
if presence:
    print("Device present")
else:
    print("No device")

DS = ds18x20.DS18X20(ow)
roms = DS.scan()


template = """<!DOCTYPE html>
<html>
<head> <title>Temperature</title> </head>
<body> <h1>Current Temperature</h1>
Hello Pico W Server World <br/>
The Temperature is: <!--#temp--><br/>
</body>
</html>
"""

addr = socket.getaddrinfo('0.0.0.0', 443)[0][-1]

s = socket.socket()
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.bind(addr)
s.listen(5)

while True:
    cl, addr = s.accept()
    print('client connected from', addr)
    client_s =None
   
    try:
        client_s = ssl.wrap_socket(cl, server_side=True, key=key, cert=cert)

        print("wrapped",client_s)
        while True:
            h = client_s.readline()
            if h == b"" or h == b"\r\n":
                    break
            print(h.decode(), end="")

        DS.convert_temp()
        temp = DS.read_temp(roms[0])

        html=template.replace("<!--#temp-->",str(temp))
        headers = ("HTTP/1.1 200 OK\r\n"
                "Content-Type: text/html; charset=UTF-8\r\n"
                "Server:Pico\r\n"
                f"Content-Length:{len(html)}\r\n\r\n"
                )
        buf = headers.encode("utf-8")+html.encode("utf-8")

        client_s.write(buf)
        client_s.close()
    except Exception as e:
       print("exception ",e)

s.close()

Page 315

import uasyncio

async def count(n):
    for i in range(n):
        print(i)
    return n

async def main(myValue):
    t1 = uasyncio.create_task(count(10))  
    print("Hello Coroutine World")
    await uasyncio.sleep(5)
    result = await t1
    print("The result of the task =",result)
    return myValue

result= uasyncio.run(main(42))
print(result)

Page 317

import uasyncio
async def test1(msg):
    print(msg)
    return msg

async def main():
    result = await uasyncio.gather(test1("one"),test1("two"))
    print(result)
    print("Hello Coroutine World")

uasyncio.run(main())

Page 319

import uasyncio
async def test1(msg):
    try:
        await uasyncio.sleep(0)      
    except:
        pass
    print(msg)
    return msg

async def main():
    t1 = uasyncio.create_task(test1("one"))
    await uasyncio.sleep(0)
    t1.cancel()
    print("Hello Coroutine World")
    await uasyncio.sleep(0)

uasyncio.run(main())

Page 319

import uasyncio

async def test(msg):
    print(msg)
    raise Exception("Test exception")


async def main():
    t1=uasyncio.create_task(test("one"))
    try:
        await t1
    except:
        print("an exception has occurred")
    print("Hello Coroutine World")
    await uasyncio.sleep(0)

uasyncio.run(main())

Page 320

import uasyncio

async def test(msg):
    print(msg)
    raise Exception("Test exception")


async def main():
    t1=uasyncio.create_task(test("one"))
    result=None
    try:
        result=await uasyncio.gather(t1,return_exceptions=True)
    except:
        print("an exception has occurred")
    print("Hello Coroutine World")
    print(result)
    await uasyncio.sleep(0)

uasyncio.run(main())

Page 322

import uasyncio

async def count():
    global myCounter
    for i in range(1000):
        temp = myCounter+1
        await uasyncio.sleep(0)
        myCounter = temp

async def main():
    await uasyncio.gather(count(),count())
    print(myCounter)

myCounter=0
uasyncio.run(main())

Page 323

import uasyncio

async def count():
    global myCounter
    global myLock
    for i in range(1000):
        async with myLock:
            temp=myCounter+1
            await uasyncio.sleep(0)
            myCounter=temp


async def main():
    await uasyncio.gather(count(),count())
    print(myCounter)

myCounter=0
myLock=uasyncio.Lock()
uasyncio.run(main())

Page 324

import uasyncio
from machine import Pin

async def blink(led, period_ms):
    while True:
        led.on()
        await uasyncio.sleep_ms(5)
        led.off()
        await uasyncio.sleep_ms(period_ms)

async def main(led1, led2):
    uasyncio.create_task(blink(led1, 700))
    uasyncio.create_task(blink(led2, 400))
    await uasyncio.sleep_ms(10_000)

uasyncio.run(main(Pin(0,Pin.OUT), Pin(1,Pin.OUT)))

Page 325

import uasyncio
from machine import Pin
from time import sleep_ms
async def blink(led, period_ms):
    while True:
        led.on()
        await uasyncio.sleep_ms(5)
        led.off()
        await uasyncio.sleep_ms(period_ms)

async def timewaste():
    while True:
        sleep_ms(10)
        await uasyncio.sleep_ms(0)


async def main(led1, led2):
    uasyncio.create_task(blink(led1, 700))
    uasyncio.create_task(blink(led2, 400))
    uasyncio.create_task(timewaste())
    await uasyncio.sleep_ms(10_000)

Page 327

import uasyncio
from time import sleep_ms
from machine import Pin, Timer
import rp2
import network


def setup(country, ssid, key):
    rp2.country(country)
    wifi=network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED=Pin("LED", Pin.OUT)
    LED.high()
    timeout=20000
    wifi.connect(ssid,key)
    timer=Timer()
    timer.init(period=200, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    s=0
    while timeout>0:
        s=wifi.status()
        if s==3 or s<0:
            break
        sleep_ms(100)
        timeout=timeout-100
   
    if(s<2):
        timer.init(period=1000, mode=Timer.PERIODIC,
                            callback=lambda t:LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi
   
async def main():
    reader,writer= await uasyncio.open_connection("www.example.com",80)
    request = b"GET /index.html HTTP/1.1\r\nHost:example.org\r\n\r\n"
    writer.write(request)
    await writer.drain()
    print(await reader.read(512))
    reader.close()
wifi = setup(country, ssid, key)
uasyncio.run(main())

Page 330

import uasyncio
import network
import rp2
from machine import Pin, Timer
from time import sleep_ms
import onewire
import ds18x20


def setup(country, ssid, key):
    rp2.country(country)
    wifi=network.WLAN(network.STA_IF)
    wifi.active(True)
    wifi.disconnect()
    LED=Pin("LED", Pin.OUT)
    LED.high()
    timeout=20000
    wifi.connect(ssid,key)
    timer=Timer()
    timer.init(period=200, mode=Timer.PERIODIC, callback=lambda t:LED.toggle())
    s=0
    while timeout>0:
        s=wifi.status()
        if s==3 or s<0:
            break
        sleep_ms(100)
        timeout=timeout-100
   
    if(s<2):
        timer.init(period=1000, mode=Timer.PERIODIC,callback=lambda t:LED.toggle())
    else:
        timer.deinit()
        LED.high()
    return wifi



wifi = setup("country", "ssid", "key")

ow = onewire.OneWire(Pin(22))
presence = ow.reset()
if presence:
    print("Device present")
else:
    print("No device")

DS = ds18x20.DS18X20(ow)
roms = DS.scan()

template = """<!DOCTYPE html>
<html>
<head> <title>Temperature</title> </head>
<body> <h1>Current Temperature</h1>
Hello Pico W Server World <br/>
The Temperature is: <!--#temp--><br/>
</body>
</html>
"""
async def serve_client(reader,writer):
    print("client")
    print(await reader.read(512))
    DS.convert_temp()
    temp = DS.read_temp(roms[0])
    html=template.replace("<!--#temp-->",str(temp))
    headers = ("HTTP/1.1 200 OK\r\n"
            "Content-Type: text/html; charset=UTF-8\r\n"
            "Server:Pico\r\n"
            f"Content-Length:{len(html)}\r\n\r\n"
            )
    buf = headers.encode("utf-8")+html.encode("utf-8")
   
    writer.write(buf)
    await writer.drain()
    writer.close()
    await writer.wait_closed()

async def main():
    await uasyncio.start_server(serve_client, '192.168.253.58', 80,backlog=5)
    while True:
        print("heartbeat")
        await uasyncio.sleep(1)

uasyncio.run(main())

Page 336

from machine import mem32, Pin
from time import sleep_ms
led = Pin(25, mode=Pin.OUT)
addrSIO = 0xd0000000
while True:
    mem32[addrSIO + 0x014] = 1 << 25
    sleep_ms(500)
    mem32[addrSIO + 0x018] = 1 << 25
    sleep_ms(500)

Page 338

from machine import Pin
import machine


def gpio_get():
    return machine.mem32[0xd0000000+0x010]


def gpio_set(value, mask):
    machine.mem32[0xd0000000+0x01C] =
    (machine.mem32[0xd0000000+0x010]) ^ value & mask


pin = Pin(22, Pin.OUT)
pin = Pin(21, Pin.OUT)
value1 = 1 << 22 | 0 << 21
value2 = 0 << 22 | 1 << 21
mask = 1 << 22 | 1 << 21
while True:
    gpio_set(value1, mask)
    gpio_set(value2, mask)

Page 344

import  _thread
counter=0

def task():    
    global counter
    print("thread started")
    for i in range(1000):
        counter=counter+1        

_thread.start_new_thread(task,())
for i in range(1000):
        counter=counter+1
time.sleep(0.5)    
print(counter)

Page 345

import time, _thread, machine
counter=0
myLock=_thread.allocate_lock()
def task():
   
    global counter, myLock
    print("thread started")
    print(myLock.locked())
    for i in range(1000):
        myLock.acquire()
        time.sleep_us(1)
        counter=counter+1        
        myLock.release()
        time.sleep_us(1)

_thread.start_new_thread(task,())

for i in range(1000):
        myLock.acquire()
        time.sleep_us(1)
        counter=counter+1
        myLock.release()
        time.sleep_us(1)
time.sleep(0.5)
print(counter)

Program Listings

Programmer’s Python: Everything is Data

pythondata360

 

We have decided not to make the programs available as a download because this is not the point of the book - the programs are not finished production code but something you should type in and study.

The best solution is to provide the source code of the programs in a form that can be copied and pasted into Thonny or VS Code project. 

The only downside is that you have to create a project to paste the code into.

To do this follow the instructions in the book.

All of the programs below were copy and pasted from working programs in the IDE. They have been formatted using the built in formatter and hence are not identical in layout to the programs in the book. This is to make copy and pasting them easier. The programs in the book are formatted to be easy to read on the page.

If anything you consider important is missing or if you have any requests or comments  contact:

This email address is being protected from spambots. You need JavaScript enabled to view it. 

Page 34

f = 1
k = 1
while(True):
    k=k+1
    f=f*k
    print(f,k)

Page 38

pi = 0
k = 1
while True:
    pi += 4 * (-1)**(k+1) * 1 / (2*k-1)
    k = k+1
    print(k, pi)

import fractions
pi = 0
k = 1
while True:
    pi += 4*(-1)**(k+1)*fractions.Fraction(1, 2*k-1)
    k = k+1
    print(k, pi, float(pi))

Page 49

import random
def myFunction(param1 = random.random()):
    print(param1)
myFunction()
myFunction()

import random
def myFunction(param1 = None):
    param1 = param1 or random.random()
    print(param1)
myFunction()
myFunction()

Page 64

import datetime
import zoneinfo

dt1 = datetime.datetime(2022, 1, 14, 10, 50, tzinfo=zoneinfo.ZoneInfo("Europe/Madrid"))
dt2 = datetime.datetime(2022, 1, 14, 10, 50, tzinfo=zoneinfo.ZoneInfo("utc"))
print(dt1.timestamp())
print(dt2.timestamp())

import datetime
import zoneinfo
dt1 = datetime.datetime(2022, 1, 14, 10, 50,
tzinfo=zoneinfo.ZoneInfo("Europe/Madrid"))
dt2 = dt1.replace(tzinfo=zoneinfo.ZoneInfo("utc"))
print(dt1)
print(dt2)

Page 65

import datetime
import zoneinfo
dt1 = datetime.datetime(2022, 1, 14, 10, 50, tzinfo=zoneinfo.ZoneInfo("Europe/Madrid"))
dt2 = dt1.astimezone(tz=zoneinfo.ZoneInfo("utc"))
print(dt1)
print(dt2)

Page 140

import random

class randItIterator():
    def __next__(self):
        return random.random()
    def __iter__(self):
        return self

class randIt(object):
    def __iter__(self):
        return randItIterator()  
     
numbers=randIt()
for x in numbers:
    print(x)

Page 142

import random
class randListIterator():
    def __init__(self,rndList):
        self._n = 0
        self._data = rndList.data
    def __next__(self):
        if self._n >= len(self._data):
            raise StopIteration
        next = self._data[self._n]
        self._n = self._n+1
        return next
       
class randList(object):
    def __init__(self):
        self.data = []
        for i in range(5):
            self.data.append(random.random())
    def __iter__(self):
        return randListIterator(self)

numbers = randList()
for x in numbers:
    print(x)
for x in numbers:
    print(x)

Page 182

class Tree:
    class Node:
        def __init__(self, value):
            self.left = None
            self.right = None
            self.value = value

    class TreeIter():
        def __init__(self, tree):
            self.stack = []
            self.currentNode = tree.root

        def __iter__(self):
            return self

        def __next__(self):
            node = self.currentNode
            if node is None:
                raise StopIteration
            if node.right is not None:
                self.stack.append(node.right)
            if node.left is not None:
                self.currentNode = node.left
            elif len(self.stack) > 0:
                self.currentNode = self.stack.pop()
            else:
                self.currentNode = None
            return node

    def __init__(self, value):
        self.root = Tree.Node(value)

    def __iter__(self):
        return Tree.TreeIter(self)

    def appendBinarySearch(self, value):
        node = self.root
        while True:
            if node.value > value:
                if node.left is None:
                    node.left = self.Node(value)
                    return
                node = node.left
            else:
                if node.right is None:
                    node.right = self.Node(value)
                    return
                node = node.right

    def appendBreathFirst(self, value):
        queue = [self.root]
        while len(queue) > 0:
            node = queue.pop(0)
            if node.left is None:
                node.left = Tree.Node(value)
                return node.left
            queue.append(node.left)
            if node.right is None:
                node.right = Tree.Node(value)
                return node.right
            queue.append(node.right)


tree = Tree(0)
for i in range(1, 15):
    tree.appendBreathFirst(i)
for node in tree:
    print(node.value)

tree = Tree(8)
for i in [3, 10, 1, 6, 14, 4, 7, 13]:
    tree.appendBinarySearch(i)
for node in tree:
    print(node.value)

Page 211

import random

msg=b"Hello World Of Secrets"
oneTime=random.randbytes(len(msg))
crypt= bytes([a^b for a, b in zip(msg,oneTime)])
print(crypt)
decrypt= bytes([a^b for a, b in zip(crypt,oneTime)])
print(decrypt)

Page 225

import pathlib

path = pathlib.Path("myBinFile.bin")
bytes = bytes([0xAA, 0x55, 0xAA, 0x55])

f = open(path, mode="wb")
f.write(bytes)
f.close()

f = open(path, mode="rb")
bytes = f.read(4)
f.close()
print(bytes.hex(","))

Page 226

import pathlib

path = pathlib.Path("myBinFile.bin")

myValue1 = 1234
f = path.open(mode="wb")
f.write(myValue1.to_bytes(4, byteorder="big"))
f.close()

f = path.open(mode="rb")
b = f.read(4)
f.close()

myValue2 = int.from_bytes(b, byteorder="big")
print(myValue2)
 
 
import pathlib

path = pathlib.Path("myBinFile.bin")

myString1 = "Hello World"
b = myString1.encode(encoding="utf8")

f = path.open(mode="wb")
n = f.write(b)
f.close()

f = path.open(mode="rb")
b = f.read(n)
f.close()

myString2 = b.decode(encoding="utf-8")
print(myString2)

Page 227

import pathlib

path = pathlib.Path("myBinFile.bin")

myString1 = "Hello World"

b = myString1.encode(encoding="utf8")
n = len(b)

f = path.open(mode="wb")
f.write(n.to_bytes(4, byteorder="big"))
m = f.write(b)
f.close()
if m != n:
    print("file error")

f = path.open(mode="rb")
b = f.read(4)
n = int.from_bytes(b, byteorder="big")
b = f.read(n)
f.close()

myString2 = b.decode(encoding="utf-8")
print(myString2)

Page 230

import pathlib
import struct

def floatToBytes(f):
    return struct.pack(">d",f)
def floatFromBytes(b):
    return struct.unpack(">d",b)[0]

path = pathlib.Path("myBinFile.bin")

myFloat = 3.14159

f = path.open(mode="wb")
m = f.write(floatToBytes(myFloat))
f.close()

f = path.open(mode="rb")
b = f.read(8)
f.close()

myFloat = floatFromBytes(b)
print(myFloat)

Page 234

import dataclasses
import struct
import pathlib


@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0
    myStruct= struct.Struct(">25sld")
    def save(self,path):
        b=person.myStruct.pack(self.name.encode(encoding="utf8"),
                                             self.id,self.score)
        f=path.open(mode="wb")
        f.write(b)
        f.close()

    def load(self,path):
        f=path.open(mode="rb")
        b=f.read(37)
        f.close()
        a,b,c=person.myStruct.unpack(b)
        self.name=a.decode(encoding="utf8").rstrip("\0x00")
        self.id=b
        self.score=c

path=pathlib.Path("myBinFile.bin")

me=person("mike",42,3.14)
me.save(path)

me2=person()
me2.load(path)
print(me2)
 

Page 235

import dataclasses
import struct
import pathlib
import os

@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0
    myStruct= struct.Struct(">25sld")
    n=37

    def save(self,f):
        b=person.myStruct.pack(
             self.name.encode(encoding="utf8"),self.id,self.score)
        f.write(b)
   
    def load(self,f,id):
        f.seek(id*person.n,0)
        b=f.read(person.n)
        a,b,c=person.myStruct.unpack(b)
        self.name=a.decode(encoding="utf8").rstrip("\0x00")
        self.id=b
        self.score=c



path=pathlib.Path("myBinFile.bin")
os.remove(path)
f=path.open(mode="ab")

me=person("mike",42,3.14)
for id in range(50):
    me.id=id
    me.save(f)
f.close()

f=path.open(mode="r+b")
me2=person()
me2.load(f,20)
print(me2)
me2.load(f,5)
print(me2)
f.close()

Page 235

import dataclasses
import struct
import pathlib
import os

@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0
    myStruct= struct.Struct(">25sld")
    n=37

    def save(self,f):
        b=person.myStruct.pack(
             self.name.encode(encoding="utf8"),self.id,self.score)
        f.write(b)
   
    def load(self,f,id):
        f.seek(id*person.n,0)
        b=f.read(person.n)
        a,b,c=person.myStruct.unpack(b)
        self.name=a.decode(encoding="utf8").rstrip("\0x00")
        self.id=b
        self.score=c



path=pathlib.Path("myBinFile.bin")
os.remove(path)
f=path.open(mode="ab")

me=person("mike",42,3.14)
for id in range(50):
    me.id=id
    me.save(f)
f.close()

f=path.open(mode="r+b")
me2=person()
me2.load(f,20)
print(me2)
me2.load(f,5)
print(me2)
f.close()

Page 248

import pathlib
import dataclasses
import csv

@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0

me = person("mike", 42, 3.145)
path = pathlib.Path("myTextFile.csv")

with path.open(mode="wt", newline="") as f:
    peopleWriter = csv.writer(f)
    for i in range(43):
        peopleWriter.writerow([me.name, i, me.score])

with path.open(mode="rt") as f:
    peopleReader = csv.reader(f)
    for row in peopleReader:
        print(row)

Page 251

import pathlib
import dataclasses
import csv

@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0
    def values(self):
        return [self.name,str(self.id),str(self.score)]
   
class MyCSV(csv.Dialect):
    quoting =csv.QUOTE_NONNUMERIC
    delimiter      = ','
    quotechar      = '"'
    lineterminator = '\r\n'

me=person("mike",42,3.145)
path=pathlib.Path("myTextFile.csv")

with path.open(mode="wt",newline="") as f:
    peopleWriter=csv.writer(f,dialect=MyCSV)
    for i in range(43):
        peopleWriter.writerow([me.name,i,me.score])
       
with path.open(mode="rt") as f:
    peopleReader=csv.reader(f,dialect=MyCSV)
    for row in peopleReader:
        print(row)

Page 256

import pathlib
import dataclasses
import json

@dataclasses.dataclass
class person:
    name:str=""
    id:int=0
    score:float=0.0
   

me=person("mike",42,3.145)

path=pathlib.Path("myTextFile.json")

with path.open(mode="wt") as f:
    s=json.dumps(dataclasses.asdict(me))
    print(s,file=f)
       
with path.open(mode="rt") as f:
    for line in f:
        data= json.loads(line)
        me1=person(**data)
        print(me1)

Page 260

from ast import parse
import pathlib
import xml.etree.ElementTree

data="""
<Books>
    <Book rating="5">
First book on Python
        <Title>
Programmer's Python: Everything is an Object
        </Title>
        <Author>
Mike James
        </Author >
        <Publisher >
IO Press
        </Publisher>
    </Book>
    <Book rating="5">
        <Title>
The Programmer’s Guide To Theory
        </Title>
        <Author>
Mike James
        </Author >
        <Publisher >
IO Press
        </Publisher>
    </Book>
</Books>
"""

path=pathlib.Path("myTextFile.xml")
rootElement=xml.etree.ElementTree.fromstring(data)
tree=xml.etree.ElementTree.ElementTree(rootElement)
tree.write(path)

Page 265

import pathlib
import pickle

path=pathlib.Path("myBinaryFile.pickle")
data=[1,2,{"name":"mike","id":42,"score":3.145}]
with path.open(mode="wb") as f:
    pickle.dump(data,f)
with path.open(mode="rb") as f:
    print(pickle.load(f))
import pathlib
import dataclasses
import pickle

@dataclasses.dataclass
class Person:
    name:str=""
    id:int=0
    score:float=0.0
    def display(self):
        print(self.name)

me=Person("mike",42,3.14)
path=pathlib.Path("myBinaryFile.pickle")
with path.open(mode="wb") as f:
    pickle.dump(me,f)
with path.open(mode="rb") as f:
    me2=pickle.load(f)
me2.display()

Page 268

import pathlib
import pickle

class readFile():
    def __init__(self):
        self.path=pathlib.Path("myFile.txt")
        self.f= self.path.open(mode="rt")
        self.pos=self.f.tell()
    def get(self):
        return self.f.readline()  
    def __getstate__(self):
        self.pos=self.f.tell()
        state = self.__dict__.copy()
        del state['f']
        return state
    def __setstate__(self, state):
        self.__dict__.update(state)
        self.f= self.path.open(mode="rt")
        self.f.seek(self.pos)  
 
read1=readFile()
print(read1.get())

path=pathlib.Path("myTemp.pickle")
with path.open(mode="wb") as f:
    pickle.dump(read1,f)

with path.open(mode="rb") as f:
    read2=pickle.load(f)
print(read2.get())

Page 287

from math import log2
import numbers
import collections.abc


class Tree(collections.abc.Sequence):
 
    class Node:
        def __init__(self,value):
            self.left=None
            self.right=None
            self.value=value

    def __init__(self,value):
        self.root=Tree.Node(value)
        self.len=1
         
 

    def appendBreathFirst(self,value):
        queue=[self.root]
        while len(queue)>0:
            node=queue.pop(0)
            if node.left is None:
                node.left=Tree.Node(value)
                self.len+=1
                return node.left
            queue.append(node.left)
            if node.right is None:
                node.right=Tree.Node(value)
                self.len+=1
                return node.right
            queue.append(node.right)

    def getNode(self,key):
        if key>=len(self) or key<0:
            raise IndexError('Index out of range')
        if key==0:
            return self.root
        row=int(log2(key+1))
        currentNode=self.root
        for r in range(1,row+1):
            k=int((key+1)/2**(row-r)-1)
            if k%2 :
                currentNode=currentNode.left
            else:
                currentNode=currentNode.right
        return currentNode

    def setNode(self,key,node):
        row=int(log2(key+1))
        currentNode=self.root
       
        for r in range(1,row):
            f=2**(row-r)
            k=int((key+1- f)/f)
           
            if k%2 :
                currentNode=currentNode.left
            else:
                currentNode=currentNode.right
        if key%2 :
            currentNode.left=node
        else:
            currentNode.right=node
   
    def __len__(self):
        return self.len

    def __getitem__(self,key):
        if isinstance(key,slice):
            temp=[]
            for i in range(0,len(self))[key]:
                temp.append(self.getNode(i))
            return temp
        if isinstance(key,int):

            return self.getNode(key)
        raise TypeError("invalid index")
                         
    def __setitem__(self,key,value):
        if isinstance(key,slice) and isinstance(value,list):
            for i in range(0,len(self))[key]:
                self.getNode(i).value=value.pop(0)
        elif isinstance(key,int):
            self.getNode(key).value=value
        else:
            raise TypeError("invalid index or value")    
   
    def __imul__(self,m):
        if isinstance(m,numbers.Number):
            for i in range(0,len(self)):
                self.getNode(i).value*= m
        return self

    def __eq__(self,otherTree):
        if not isinstance(otherTree,Tree):
            return NotImplemented

        if len(self)!=len(otherTree):
            return False
        for i in range(0,len(self)):
                if self.getNode(i).value!= otherTree.getNode(i).value:
                    return False
        return True
   
    def __hash__(self):
        temp=[]
        for i in range(0,len(self)):
            temp.append(self.getNode(i).value)
        return hash(tuple(temp))