cake
/
libcasio
Archived
1
1
Fork 0

More edits, I don't really know at this point

This commit is contained in:
Thomas Touhey 2018-06-18 15:30:16 +02:00
parent 8f01bf4eaf
commit e48998015b
No known key found for this signature in database
GPG Key ID: 2ECEB0517AD947FB
66 changed files with 1759 additions and 1174 deletions

View File

@ -24,6 +24,7 @@
# include "libcasio/log.h"
# include "libcasio/number.h"
# include "libcasio/misc.h"
# include "libcasio/link.h"
# include "libcasio/file.h"

View File

@ -1,150 +0,0 @@
/* ****************************************************************************
* libcasio/builtin.h -- libcasio built-in platform-specific things.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LIBCASIO_BUILTIN_H
# define LIBCASIO_BUILTIN_H
# include "cdefs.h"
# include "stream.h"
# include "fs.h"
# ifndef LIBCASIO_DISABLED_FILE
# include <stdio.h>
# endif
CASIO_BEGIN_NAMESPACE
CASIO_BEGIN_DECLS
/* ---
* Built-in streams.
* --- */
/* Make a stream using the standard FILE interface. */
# ifndef LIBCASIO_DISABLED_FILE
CASIO_EXTERN int CASIO_EXPORT casio_open_stream_file
OF((casio_stream_t **casio__stream,
FILE *casio__readstream, FILE *casio__writestream,
int casio__close_readstream, int casio__close_writestream));
# endif
/* Make a stream using the POSIX STREAMS interface. */
# if defined(__linux__) || (defined(__APPLE__) && defined(__MACH__))
CASIO_EXTERN int CASIO_EXPORT casio_opencom_streams
OF((casio_stream_t **casio__stream, const char *casio__path));
CASIO_EXTERN int CASIO_EXPORT casio_open_stream_streams
OF((casio_stream_t **casio__stream,
const char *casio__path, casio_openmode_t casio__mode));
CASIO_EXTERN int CASIO_EXPORT casio_open_stream_fd
OF((casio_stream_t **casio__stream,
int casio__readfd, int casio__writefd,
int casio__closeread, int casio__closewrite));
# else
# define LIBCASIO_DISABLED_STREAMS
# endif
/* Make a stream using libusb. */
# ifndef LIBCASIO_DISABLED_LIBUSB
CASIO_EXTERN int CASIO_EXPORT casio_openusb_libusb
OF((casio_stream_t **casio__stream,
int casio__bus, int casio__address));
# endif
/* Make a stream using the Microsoft Windows API. */
# if defined(_WIN16) || defined(_WIN32) || defined(_WIN64) \
|| defined(__WINDOWS__)
CASIO_EXTERN int CASIO_EXPORT casio_openusb_windows
OF((casio_stream_t **casio__stream,
int casio__bus, int casio__address));
CASIO_EXTERN int CASIO_EXPORT casio_opencom_windows
OF((casio_stream_t **casio__stream, const char *casio__path));
# else
# define LIBCASIO_DISABLED_WINDOWS
# endif
/* ---
* Built-in filesystems.
* --- */
/* Make a POSIX filesystem interface. */
# if defined(__linux__) || (defined(__APPLE__) && defined(__MACH__))
CASIO_EXTERN int CASIO_EXPORT casio_open_posix_fs
OF((casio_fs_t **casio__filesystem));
# else
# define LIBCASIO_DISABLED_POSIX_FS 1
# endif
/* Make a Windows API filesystem interface. */
# ifndef LIBCASIO_DISABLED_WINDOWS
CASIO_EXTERN int CASIO_EXPORT casio_open_windows_fs
OF((casio_fs_t **casio__filesystem));
# endif
/* ---
* Built-in serial devices listing.
* --- */
/* List serial devices on Linux. */
# ifdef __linux__
CASIO_EXTERN int CASIO_EXPORT casio_comlist_linux
OF((casio_list_com_t *casio__callback, void *casio__cookie));
# endif
/* List serial devices on MacOS/OS X. */
# if defined(__APPLE__) && defined(__MACH__)
CASIO_EXTERN int CASIO_EXPORT casio_comlist_macos
OF((casio_list_com_t *casio__callback, void *casio__cookie));
# endif
/* List serial devices on Microsoft Windows. */
# ifndef LIBCASIO_DISABLED_WINDOWS
CASIO_EXTERN int CASIO_EXPORT casio_comlist_windows
OF((casio_list_com_t *casio__callback, void *casio__cookie));
# endif
/* ---
* Built-in functions.
* --- */
/* As there is no portable sleep function, libcasio implements one.
* It takes a callback, of the following form: */
typedef void casio_sleep_t OF((unsigned long casio__ms));
CASIO_EXTERN void CASIO_EXPORT casio_set_sleep
OF((casio_sleep_t *casio__func));
CASIO_EXTERN int CASIO_EXPORT casio_sleep
OF((unsigned long casio__ms));
/* And here are cross-platform allocation functions.
* They are defined just in case. */
CASIO_EXTERN void* CASIO_EXPORT casio_alloc
OF((size_t casio__num_elements, size_t casio__element_size));
CASIO_EXTERN void CASIO_EXPORT casio_free
OF((void *casio__ptr));
CASIO_END_DECLS
CASIO_END_NAMESPACE
#endif /* LIBCASIO_BUILTIN_H */

View File

@ -66,6 +66,43 @@
# define CASIO_MSC_PREREQ(CASIO__MAJ, CASIO__MIN) 0
# endif
/* ---
* Check for subsystems.
* --- */
/* Macros defined by the `libcasio/config.h` header:
* - `LIBCASIO_DISABLED_FILE`: can we use the standard FILE operations?
* - `LIBCASIO_DISABLED_LIBUSB`: can we use libusb? */
/* Can we use the Linux and the MacOS/OS X listing?
* XXX: what about Linux distributions not using the Linux standard
* filesystem? */
# if defined(__linux__)
# else
# define LIBCASIO_DISABLED_LINUX_SERIAL
# endif
# if defined(__APPLE__) && defined(__MACH__)
# else
# define LIBCASIO_DISABLED_MAC_SERIAL
# endif
/* Can we use the POSIX (STREAMS) interface? */
# if defined(__linux__) || (defined(__APPLE__) && defined(__MACH__))
# else
# define LIBCASIO_DISABLED_STREAMS
# endif
/* Can we use the Windows (Win32/Win64) API? */
# if defined(_WIN16) || defined(_WIN32) || defined(_WIN64) \
|| defined(__WINDOWS__)
# else
# define LIBCASIO_DISABLED_WINDOWS
# endif
/* ---
* Extern functions.
* --- */

View File

@ -28,9 +28,9 @@ CASIO_BEGIN_NAMESPACE
CASIO_BEGIN_DECLS
CASIO_EXTERN int CASIO_EXPORT casio_decode_date
OF((time_t *casio__date, const char *casio__raw));
OF((time_t *casio__date, char const *casio__raw));
CASIO_EXTERN int CASIO_EXPORT casio_encode_date
OF((char *casio__raw, const time_t *casio__date));
OF((char *casio__raw, time_t const *casio__date));
CASIO_END_DECLS

View File

@ -61,9 +61,12 @@ typedef int casio_error_t;
* stream has failed */
# define casio_error_noseek 0x13 /* (alias) */
# define casio_error_timeout 0x14 /* a timeout has occured. */
# define casio_error_time 0x14 /* (alias) */
# define casio_error_access 0x15 /* could not access the device (perms) */
# define casio_error_noaccess 0x15 /* (alias) */
# define casio_error_eof 0x16 /* end of file */
# define casio_error_scsi 0x17 /* a SCSI operation has failed. */
# define casio_error_usb 0x18 /* a USB operation has failed. */
/* Link errors. */
@ -101,9 +104,9 @@ typedef int casio_error_t;
/* Get a string describing the error. */
CASIO_EXTERN const char* CASIO_EXPORT casio_error_strings[];
CASIO_EXTERN char const* CASIO_EXPORT casio_error_strings[];
CASIO_EXTERN const char* CASIO_EXPORT casio_strerror
CASIO_EXTERN char const* CASIO_EXPORT casio_strerror
OF((int casio__error));
# ifndef LIBCASIO_NO_STRERROR

View File

@ -121,8 +121,8 @@ CASIO_EXTERN int CASIO_EXPORT casio_make_lang
CASIO_EXTERN int CASIO_EXPORT casio_make_addin
OF((casio_file_t **casio__handle,
casio_filefor_t casio__for, size_t casio__size,
const char *casio__name, const char *casio__internal,
const casio_version_t *casio__version, const time_t *casio__created));
char const *casio__name, char const *casio__internal,
casio_version_t const *casio__version, time_t const *casio__created));
/* Free a file. */
@ -133,13 +133,13 @@ CASIO_EXTERN void CASIO_EXPORT casio_free_file
CASIO_EXTERN int CASIO_EXPORT casio_decode
OF((casio_file_t **casio__handle,
const char *casio__path, casio_stream_t *casio__buffer,
char const *casio__path, casio_stream_t *casio__buffer,
casio_filetype_t casio__expected_types));
/* Open and decode a file. */
CASIO_EXTERN int CASIO_EXPORT casio_open_file
OF((casio_file_t **casio__handle,
const char *casio__path, casio_filetype_t casio__expected_types));
char const *casio__path, casio_filetype_t casio__expected_types));
#endif /* LIBCASIO_FILE_H */

View File

@ -80,61 +80,32 @@ struct casio_path_s {
/* This structure defines file metadata.
* Here are the flags:
* `CASIO_STAT_FLAG_PERM`: stat permissions are set;
* `CASIO_STAT_FLAG_BTIME`: birth time is set;
* `CASIO_STAT_FLAG_ATIME`: last accessed time is set;
* `CASIO_STAT_FLAG_MTIME`: last modif. time is set. */
# define CASIO_STAT_FLAG_PERM 0x0001
# define CASIO_STAT_FLAG_BTIME 0x0002
# define CASIO_STAT_FLAG_ATIME 0x0004
# define CASIO_STAT_FLAG_MTIME 0x0008
/* Elements can have Unix-like permissions. Here they are:
* `CASIO_STAT_PERM_IRUSR`: user has read permission;
* `CASIO_STAT_PERM_IWUSR`: user has write permission;
* `CASIO_STAT_PERM_IXUSR`: user has exec permission;
* `CASIO_STAT_PERM_IRGRP`: group has read permission;
* `CASIO_STAT_PERM_IWGRP`: group has write permission;
* `CASIO_STAT_PERM_IXGRP`: group has exec permission;
* `CASIO_STAT_PERM_IROTH`: others have read permission;
* `CASIO_STAT_PERM_IWOTH`: others have write permission;
* `CASIO_STAT_PERM_IXOTH`: others have exec permission. */
# define CASIO_STAT_PERM_IRUSR 0x0001
# define CASIO_STAT_PERM_IWUSR 0x0002
# define CASIO_STAT_PERM_IXUSR 0x0004
# define CASIO_STAT_PERM_IRGRP 0x0010
# define CASIO_STAT_PERM_IWGRP 0x0020
# define CASIO_STAT_PERM_IXGRP 0x0040
# define CASIO_STAT_PERM_IROTH 0x0100
# define CASIO_STAT_PERM_IWOTH 0x0200
# define CASIO_STAT_PERM_IXOTH 0x0400
# define CASIO_STAT_FLAG_BTIME 0x0001
# define CASIO_STAT_FLAG_ATIME 0x0002
# define CASIO_STAT_FLAG_MTIME 0x0004
/* And here are the "file" types ("file" is between quotes as on Windows,
* directories are not files like on Unix) you can find:
* `CASIO_STAT_TYPE_OTH`: other type of file.
* `CASIO_STAT_TYPE_REG`: regular file;
* `CASIO_STAT_TYPE_DIR`: directory;
* `CASIO_STAT_TYPE_LNK`: symbolic link;
* `CASIO_STAT_TYPE_CHAR`: character device;
* `CASIO_STAT_TYPE_BLK`: block device;
* `CASIO_STAT_TYPE_SOCK`: socket */
* `CASIO_STAT_TYPE_DIR`: directory; */
# define CASIO_STAT_TYPE_OTH 0x0000
# define CASIO_STAT_TYPE_REG 0x0001
# define CASIO_STAT_TYPE_DIR 0x0002
# define CASIO_STAT_TYPE_LNK 0x0004
# define CASIO_STAT_TYPE_CHAR 0x0008
# define CASIO_STAT_TYPE_BLK 0x0010
# define CASIO_STAT_TYPE_SOCK 0x0020
/* And here is the stat structure. The elements it contains at runtime depend
* on the flags (useful for binary compatibility and filesystem metadata type).
* For example, if `~thestat.casio_stat_flags & CASIO_STAT_FLAG_PERM`,
* then you shouldn't try to read the permissions, as it might contain crap.
* For example, if `~thestat.casio_stat_flags & CASIO_STAT_FLAG_MTIME`,
* then you shouldn't try to read the last modification time, as it might
* contain crap.
*
* The elements are the following:
* [ ] `casio_stat_type`: the file type (see the `CASIO_STAT_TYPE_*` macros);
* [X] `casio_stat_perm`: Unix-like permissions (see `CASIO_STAT_PERM_*`);
* [X] `casio_stat_size`: the file size;
* [X] `casio_stat_btime`: the file's birth time;
* [X] `casio_stat_atime`: the file's last access time;
@ -150,8 +121,6 @@ struct casio_path_s {
struct casio_stat_s {
unsigned short casio_stat_flags;
unsigned short casio_stat_type;
unsigned short casio_stat_perm;
unsigned short casio_stat__reserved;
casio_off_t casio_stat_size;
time_t casio_stat_btime;
@ -166,7 +135,7 @@ struct casio_stat_s {
* `casio_duplicate_pathnode`! */
typedef void CASIO_EXPORT casio_fs_list_func_t OF((void *casio__cookie,
const casio_pathnode_t *casio__node, const casio_stat_t *casio__stat));
casio_pathnode_t const *casio__node, casio_stat_t const *casio__stat));
/* ---
* Filesystem description.
@ -203,7 +172,7 @@ typedef int CASIO_EXPORT casio_fs_stat_t
# if defined(__STDC__) && __STDC__
typedef int CASIO_EXPORT casio_fs_make_t(void *casio__cookie,
void *casio__native_path, const casio_stat_t *casio__stat, ...);
void *casio__native_path, casio_stat_t const *casio__stat, ...);
# else
typedef int CASIO_EXPORT casio_fs_make_t();
# endif
@ -246,7 +215,7 @@ typedef int CASIO_EXPORT casio_fs_list_t
* we're only considering this operation for CASIOWIN. */
typedef int CASIO_EXPORT casio_fs_optim_t
OF((void *casio__cookie, const char *device));
OF((void *casio__cookie, char const *device));
/* And here is the structure with all of the functions.
* It is the one used when you want to open a libcasio filesystem interface

View File

@ -77,11 +77,22 @@ CASIO_BEGIN_DECLS
CASIO_EXTERN int CASIO_EXPORT casio_iter
OF((casio_iter_t **casio__iterp, void *casio__cookie,
casio_iter_funcs_t const *casio__funcs));
CASIO_EXTERN int CASIO_EXPORT casio_next
OF((casio_iter_t *casio__iter, void **casio__ptr));
CASIO_EXTERN void CASIO_EXPORT casio_end
OF((casio_iter_t *casio__iter));
/* You can make a “super iterator” that makes an iterator out of two
* iterators! It will empty the first one, then the second one.
* It will also take care of closing them. */
CASIO_EXTERN int CASIO_EXPORT casio_combine_iterators
OF((casio_iter_t **casio__iterp,
casio_iter_t *casio__first,
casio_iter_t *casio__second));
CASIO_END_DECLS
CASIO_END_NAMESPACE

View File

@ -24,6 +24,11 @@
# include "fs.h"
# include "version.h"
# include "picture.h"
# include "iter.h"
# ifndef LIBCASIO_DISABLED_FILE
# include <stdio.h>
# endif
CASIO_BEGIN_NAMESPACE
/* ---
@ -40,34 +45,41 @@ typedef struct casio_link_s casio_link_t;
/* Link information.
* This is basically the identification information sent by the calculator,
* only in Protocol 7.00 (Graph 85 and following) and CAS100 (AFX,
* Graph 100). */
* Graph 100).
*
* TODO: make flags for other information not available for AFX? */
# define casio_link_info_wiped_preprog 0x0001
# define casio_link_info_wiped_bootcode 0x0002
# define casio_link_info_wiped_os 0x0004
# define casio_link_info_flag_preprog 0x0001
# define casio_link_info_flag_bootcode 0x0002
# define casio_link_info_flag_os 0x0004
typedef struct casio_link_info_s {
unsigned int casio_link_info_wiped;
unsigned long casio_link_info_flags;
/* Preprogrammed ROM information. */
/* preprogrammed ROM information */
unsigned long casio_link_info_rom_capacity;
casio_version_t casio_link_info_rom_version;
/* flash ROM and RAM information */
/* Flash ROM and RAM information. */
unsigned long casio_link_info_flash_rom_capacity;
unsigned long casio_link_info_ram_capacity;
/* bootcode information */
/* Bootcode information. */
casio_version_t casio_link_info_bootcode_version;
unsigned long casio_link_info_bootcode_offset;
unsigned long casio_link_info_bootcode_size;
/* OS information */
/* OS information. */
casio_version_t casio_link_info_os_version;
unsigned long casio_link_info_os_offset;
unsigned long casio_link_info_os_size;
/* other information */
/* Other information. */
char casio_link_info_product_id[17];
char casio_link_info_username[17];
char casio_link_info_hwid[9];
@ -95,7 +107,7 @@ typedef void CASIO_EXPORT casio_link_progress_t
/* List files. */
typedef void CASIO_EXPORT casio_link_list_t
OF((void *casio__cookie, const char *casio__path,
OF((void *casio__cookie, char const *casio__path,
const casio_stat_t *casio__stat));
/* ---
@ -118,12 +130,42 @@ typedef struct casio_screen_s {
* Basic link handle operations.
* --- */
/* Initialization flags.
* `CASIO_LINKFLAG_ACTIVE`: start off as active;
* `CASIO_LINKFLAG_CHECK`: check (initial packet);
* `CASIO_LINKFLAG_TERM`: terminate;
/* Useful flags for when opening a link.
*
* Here are the various transport protocols, which isn't given by the available
* operations on the stream (as it could be USB but we may not be able
* to do USB operations because of drivers such as the CESG502 driver
* on Microsoft Windows):
*
* `CASIO_LINKFLAG_SERIAL`: serial connexion.
* `CASIO_LINKFLAG_USB`: USB.
* `CASIO_LINKFLAG_SCSI`: SCSI operations.
*
* These are read if the connexion is serial (which means that the
* protocol cannot be determined and that the user needs to say which one
* they want to use):
*
* `CASIO_LINKFLAG_CAS40`: CAS40 (very old protocol).
* `CASIO_LINKFLAG_CAS50`: CAS50 (old protocol).
* `CASIO_LINKFLAG_CAS100`: CAS100 (not so old protocol used on the AFX).
* `CASIO_LINKFLAG_P7`: protocol 7.00 (starting to get old but still there).
*
* These are read if the protocol is protocol 7.00:
*
* `CASIO_LINKFLAG_ACTIVE`: start off as active.
* `CASIO_LINKFLAG_CHECK`: check (initial packet).
* `CASIO_LINKFLAG_TERM`: terminate.
* `CASIO_LINKFLAG_NODISC`: if we are checking, no environment discovery. */
# define CASIO_LINKFLAG_SERIAL 0x00000000
# define CASIO_LINKFLAG_USB 0x00001000
# define CASIO_LINKFLAG_SCSI 0x00002000
# define CASIO_LINKFLAG_P7 0x00000000
# define CASIO_LINKFLAG_CAS40 0x00000100
# define CASIO_LINKFLAG_CAS50 0x00000200
# define CASIO_LINKFLAG_CAS100 0x00000300
# define CASIO_LINKFLAG_ACTIVE 0x00000001
# define CASIO_LINKFLAG_CHECK 0x00000002
# define CASIO_LINKFLAG_TERM 0x00000004
@ -131,22 +173,26 @@ typedef struct casio_screen_s {
CASIO_BEGIN_DECLS
/* Cross-platform initialization. */
/* Open a serial link. */
CASIO_EXTERN int CASIO_EXPORT casio_open_usb
OF((casio_link_t **casio__h, unsigned long casio__flags,
int casio__bus, int casio__address));
CASIO_EXTERN int CASIO_EXPORT casio_open_com
CASIO_EXTERN int CASIO_EXPORT casio_open_serial
OF((casio_link_t **casio__h, unsigned long casio__flags,
char const *casio__path,
casio_streamattrs_t const *casio__attributes));
/* Initialize a handle using a custom stream. */
/* Open a USB link. */
CASIO_EXTERN int CASIO_EXPORT casio_open_usb
OF((casio_link_t **casio__h, unsigned long casio__flags,
int casio__bus, int casio__address));
/* Initialize a handle using a custom stream.
* This function will check if the stream is a USB stream by looking
* at the open mode of the stream. */
CASIO_EXTERN int CASIO_EXPORT casio_open_link
OF((casio_link_t **casio__h,
unsigned long casio__flags, casio_stream_t *casio__stream,
casio_streamattrs_t const *casio__attributes));
OF((casio_link_t **casio__h, unsigned long casio__flags,
casio_stream_t *casio__stream));
/* De-initialize. */

View File

@ -27,13 +27,13 @@ CASIO_BEGIN_DECLS
CASIO_EXTERN void CASIO_EXPORT casio_setlog
OF((const char *casio__level));
CASIO_EXTERN const char* CASIO_EXPORT casio_getlog
CASIO_EXTERN char const* CASIO_EXPORT casio_getlog
OF((void));
/* List log levels (deprecated interface) */
typedef void casio_log_list_t OF((void *casio__cookie,
const char *casio__str));
char const *casio__str));
CASIO_EXTERN CASIO_DEPRECATED void CASIO_EXPORT casio_listlog
OF((casio_log_list_t *casio__callback, void *casio__cookie));

View File

@ -79,7 +79,7 @@ CASIO_BEGIN_DECLS
CASIO_EXTERN int CASIO_EXPORT casio_open_mcs
OF((casio_mcs_t **casio__mcs, void *casio__cookie,
const casio_mcsfuncs_t *casio__funcs));
casio_mcsfuncs_t const *casio__funcs));
CASIO_EXTERN int CASIO_EXPORT casio_close_mcs
OF((casio_mcs_t *casio__mcs));
@ -108,7 +108,7 @@ CASIO_EXTERN int CASIO_EXPORT casio_delete_mcsfile
/* List MCS files (the deprecated way). */
typedef void CASIO_EXPORT casio_mcslist_t
OF((void *casio__cookie, const casio_mcshead_t *casio__mcshead));
OF((void *casio__cookie, casio_mcshead_t const *casio__mcshead));
CASIO_EXTERN CASIO_DEPRECATED int CASIO_EXPORT casio_list_mcsfiles
OF((casio_mcs_t *casio__mcs, casio_mcslist_t *casio__mcslist,

View File

@ -261,9 +261,9 @@ CASIO_BEGIN_DECLS
/* Make a main memory file, prepare it, and free it. */
CASIO_EXTERN int CASIO_EXPORT casio_make_mcsfile
OF((casio_mcsfile_t **casio__handle, const casio_mcshead_t *casio__head));
OF((casio_mcsfile_t **casio__handle, casio_mcshead_t const *casio__head));
CASIO_EXTERN int CASIO_EXPORT casio_prepare_mcsfile
OF((casio_mcsfile_t *casio__handle, const casio_mcshead_t *casio__head));
OF((casio_mcsfile_t *casio__handle, casio_mcshead_t const *casio__head));
CASIO_EXTERN void CASIO_EXPORT casio_free_mcsfile
OF((casio_mcsfile_t *casio__handle));
@ -278,19 +278,19 @@ CASIO_EXTERN int CASIO_EXPORT casio_copy_mcsfile
CASIO_EXTERN int CASIO_EXPORT casio_decode_mcsfile_head
OF((casio_mcshead_t *casio__head, int casio__raw_type,
const unsigned char *casio__groupname,
const unsigned char *casio__dirname,
const unsigned char *casio__filename,
unsigned char const *casio__groupname,
unsigned char const *casio__dirname,
unsigned char const *casio__filename,
unsigned long casio__filesize));
CASIO_EXTERN int CASIO_EXPORT casio_decode_mcsfile
OF((casio_mcsfile_t **casio__handle,
const casio_mcshead_t *casio__head,
casio_mcshead_t const *casio__head,
casio_stream_t *casio__buffer));
CASIO_EXTERN int CASIO_EXPORT casio_decode_mcsfile_data
OF((casio_mcsfile_t **casio__handle,
const casio_mcshead_t *casio__head,
const void *casio__data, size_t casio__size));
casio_mcshead_t const *casio__head,
void const *casio__data, size_t casio__size));
CASIO_EXTERN int CASIO_EXPORT casio_encode_mcsfile
OF((casio_mcsfile_t *casio__handle, casio_stream_t *casio__buffer));

81
include/libcasio/misc.h Normal file
View File

@ -0,0 +1,81 @@
/* ****************************************************************************
* libcasio/misc.h -- libcasio miscallaneous utilities.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LIBCASIO_MISC_H
# define LIBCASIO_MISC_H 2018051601
# include "cdefs.h"
# include "stream.h"
# include "fs.h"
CASIO_BEGIN_NAMESPACE
CASIO_BEGIN_DECLS
/* As there is no portable sleep function, libcasio implements one.
* It takes a callback, of the following form: */
CASIO_EXTERN int CASIO_EXPORT casio_sleep
OF((unsigned long casio__ms));
/* If the default function is not good enough for you, just change it
* using the following function. */
typedef void casio_sleep_t OF((unsigned long casio__ms));
CASIO_EXTERN void CASIO_EXPORT casio_set_sleep_func
OF((casio_sleep_t *casio__func));
/* As for time and timeouts management, here are functions to time
* anything in libcasio. Times are expressed in milliseconds. */
struct casio_timer_s;
typedef struct casio_timer_s casio_timer_t;
CASIO_EXTERN int CASIO_EXPORT casio_get_timer
OF((casio_timer_t **casio__timer));
CASIO_EXTERN void CASIO_EXPORT casio_free_timer
OF((casio_timer_t *casio__timer));
CASIO_EXTERN int CASIO_EXPORT casio_get_spent_time
OF((casio_timer_t *casio__timer, unsigned long *casio__spent));
/* You can change these functions too! */
typedef int CASIO_EXPORT casio_get_timer_t
OF((casio_timer_t **casio__timer));
typedef void CASIO_EXPORT casio_free_timer_t
OF((casio_timer_t *casio__timer));
typedef int CASIO_EXPORT casio_get_spent_time_t
OF((casio_timer_t *casio__timer, unsigned long *casio__spent));
CASIO_EXTERN int CASIO_EXPORT casio_set_timer_funcs
OF((casio_get_timer_t *casio__get_timer,
casio_free_timer_t *casio__free_timer,
casio_get_spent_time_t *casio__get_spent_time));
/* And here are cross-platform allocation functions.
* They are defined just in case. */
CASIO_EXTERN void* CASIO_EXPORT casio_alloc
OF((size_t casio__num_elements, size_t casio__element_size));
CASIO_EXTERN void CASIO_EXPORT casio_free
OF((void *casio__ptr));
CASIO_END_DECLS
CASIO_END_NAMESPACE
#endif /* LIBCASIO_MISC_H */

View File

@ -124,28 +124,28 @@ CASIO_BEGIN_DECLS
/* From and to MCS BCD. */
CASIO_EXTERN int CASIO_EXPORT casio_bcd_frommcs
OF((casio_bcd_t *casio__bcd, const casio_mcsbcd_t *casio__raw));
OF((casio_bcd_t *casio__bcd, casio_mcsbcd_t const *casio__raw));
CASIO_EXTERN int CASIO_EXPORT casio_bcd_tomcs
OF((casio_mcsbcd_t *casio__raw, const casio_bcd_t *casio__bcd));
OF((casio_mcsbcd_t *casio__raw, casio_bcd_t const *casio__bcd));
/* From and to CAS BCD. */
CASIO_EXTERN int CASIO_EXPORT casio_bcd_fromcas
OF((casio_bcd_t *casio__bcd, const casio_casbcd_t *casio__raw));
OF((casio_bcd_t *casio__bcd, casio_casbcd_t const *casio__raw));
CASIO_EXTERN int CASIO_EXPORT casio_bcd_tocas
OF((casio_casbcd_t *casio__raw, const casio_bcd_t *casio__bcd));
OF((casio_casbcd_t *casio__raw, casio_bcd_t const *casio__bcd));
/* From and to C-double */
CASIO_EXTERN void CASIO_EXPORT casio_bcd_fromdouble
OF((casio_bcd_t *casio__bcd, double casio__raw));
CASIO_EXTERN double CASIO_EXPORT casio_bcd_todouble
OF((const casio_bcd_t *casio__bcd));
OF((casio_bcd_t const *casio__bcd));
/* Make a string out of a BCD */
CASIO_EXTERN size_t CASIO_EXPORT casio_bcdtoa
OF((char *casio__buf, size_t casio__len, const casio_bcd_t *casio__bcd));
OF((char *casio__buf, size_t casio__len, casio_bcd_t const *casio__bcd));
CASIO_END_DECLS
CASIO_END_NAMESPACE

View File

@ -223,11 +223,11 @@ CASIO_EXTERN size_t CASIO_EXPORT casio_get_picture_size
CASIO_EXTERN int CASIO_EXPORT casio_decode_picture
OF((casio_pixel_t **casio__pixels,
const void *casio__raw, casio_pictureformat_t casio__format,
void const *casio__raw, casio_pictureformat_t casio__format,
unsigned int casio__width, unsigned casio__height));
CASIO_EXTERN int CASIO_EXPORT casio_encode_picture
OF((void *casio__raw, const casio_pixel_t **casio__pixels,
OF((void *casio__raw, casio_pixel_t const * const *casio__pixels,
casio_pictureformat_t casio__format,
unsigned int casio__width, unsigned casio__height));

View File

@ -320,15 +320,18 @@ CASIO_END_DECLS
* are used depending on the packet type/code. */
typedef struct casio_seven_packet_s {
/* main info */
/* Main info. */
casio_seven_type_t casio_seven_packet_type;
int casio_seven_packet_extended;
/* error, termination, check */
/* Error, termination, check. */
int casio_seven_packet_code;
int casio_seven_packet_initial;
/* commands */
/* Commands. */
int casio_seven_packet_ow;
int casio_seven_packet_mcstype;
unsigned long casio_seven_packet_filesize;
@ -337,20 +340,24 @@ typedef struct casio_seven_packet_s {
unsigned long casio_seven_packet_loadaddr;
unsigned long casio_seven_packet_straddr;
/* data */
/* Data. */
unsigned int casio_seven_packet_id;
unsigned int casio_seven_packet_total;
unsigned int casio_seven_packet_data_size;
/* server information */
/* Server information. */
casio_link_info_t casio_seven_packet_info;
/* screen */
/* Screen. */
casio_pictureformat_t casio_seven_packet_pictype;
unsigned int casio_seven_packet_height;
unsigned int casio_seven_packet_width;
/* big things */
/* Big things. */
unsigned char casio_seven_packet_data[CASIO_SEVEN_MAX_RAWDATA_SIZE];
char casio_seven_packet__argsdata[6][CASIO_SEVEN_MAX_CMDARG_SIZE + 1];
char casio_seven_packet_vram[CASIO_SEVEN_MAX_VRAM_SIZE];

View File

@ -92,7 +92,8 @@ CASIO_BEGIN_NAMESPACE
# define casio_drawtype_con 0
# define casio_drawtype_plot 1
/* Main structure */
/* Main structure. */
typedef struct casio_setup_s {
unsigned int casio_setup_iflags;
unsigned int casio_setup_wflags;
@ -114,7 +115,7 @@ CASIO_EXTERN void CASIO_EXPORT casio_init_setup
/* Feed the structure. */
CASIO_EXTERN int CASIO_EXPORT casio_feed_setup_seven
OF((casio_setup_t *casio__setup, const char *casio__name, int casio__val));
OF((casio_setup_t *casio__setup, char const *casio__name, int casio__val));
CASIO_EXTERN int CASIO_EXPORT casio_feed_setup_mcs
OF((casio_setup_t *casio__setup, int casio__id, int casio__val));

View File

@ -27,6 +27,7 @@
#ifndef LIBCASIO_STREAM_H
# define LIBCASIO_STREAM_H
# include "cdefs.h"
# include "iter.h"
CASIO_BEGIN_NAMESPACE
/* Forward structure declarations (don't mind). */
@ -37,8 +38,6 @@ struct casio_streamfuncs_s;
typedef struct casio_streamfuncs_s casio_streamfuncs_t;
struct casio_streamattrs_s;
typedef struct casio_streamattrs_s casio_streamattrs_t;
struct casio_timeouts_s;
typedef struct casio_timeouts_s casio_timeouts_t;
struct casio_scsi_s;
typedef struct casio_scsi_s casio_scsi_t;
@ -96,33 +95,35 @@ typedef int casio_whence_t;
typedef int casio_stream_close_t OF((void *));
typedef int casio_stream_setattrs_t
OF((void *, const casio_streamattrs_t *));
typedef int casio_stream_settm_t
OF((void *, const casio_timeouts_t *));
OF((void *, casio_streamattrs_t const *));
typedef int casio_stream_read_t
OF((void *, unsigned char *, size_t));
OF((void *, unsigned char *, size_t,
unsigned int /* total timeout in ms */));
typedef int casio_stream_write_t
OF((void *, const unsigned char *, size_t));
OF((void *, unsigned char const *, size_t,
unsigned int /* total timeout in ms */));
typedef int casio_stream_seek_t
OF((void *, casio_off_t *, casio_whence_t));
typedef int casio_stream_scsi_t
OF((void *, casio_scsi_t*));
typedef int casio_stream_usb_send_bulk_t
OF((void *, unsigned char const *, size_t, int /* timeout */));
typedef int casio_stream_usb_recv_bulk_t
OF((void *, unsigned char *, size_t, int /* timeout */));
/* Here is the callbacks structure: */
struct casio_streamfuncs_s {
/* Main callbacks. */
casio_stream_close_t *casio_streamfuncs_close;
casio_stream_close_t *casio_streamfuncs_close;
casio_stream_settm_t *casio_streamfuncs_settm;
/* General read & write callbacks ("stream" origins). */
/* Read & Write callbacks. */
casio_stream_read_t *casio_streamfuncs_read;
casio_stream_write_t *casio_streamfuncs_write;
casio_stream_seek_t *casio_streamfuncs_seek;
casio_stream_read_t *casio_streamfuncs_read;
casio_stream_write_t *casio_streamfuncs_write;
casio_stream_seek_t *casio_streamfuncs_seek;
/* Serial callbacks. */
@ -130,27 +131,14 @@ struct casio_streamfuncs_s {
/* SCSI callbacks. */
casio_stream_scsi_t *casio_streamfuncs_scsi;
casio_stream_scsi_t *casio_streamfuncs_scsi;
/* USB callbacks. */
casio_stream_usb_send_bulk_t *casio_streamfuncs_usb_send_bulk;
casio_stream_usb_recv_bulk_t *casio_streamfuncs_usb_recv_bulk;
};
/* And here are some macros, for better API compatibility */
# define casio_stream_callbacks_for_serial(CASIO__CLOSE, CASIO__SETCOMM, \
CASIO__SETTM, CASIO__READ, CASIO__WRITE) \
{(casio_stream_close_t*)(CASIO__CLOSE), \
(casio_stream_settm_t*)(CASIO__SETTM), \
(casio_stream_read_t*)(CASIO__READ), \
(casio_stream_write_t*)(CASIO__WRITE), NULL, \
(casio_stream_setattrs_t*)(CASIO__SETCOMM), \
NULL}
# define casio_stream_callbacks_for_virtual(CASIO__CLOSE, \
CASIO__READ, CASIO__WRITE, CASIO__SEEK) \
{(casio_stream_close_t*)(CASIO__CLOSE), NULL, \
(casio_stream_read_t*)(CASIO__READ), \
(casio_stream_write_t*)(CASIO__WRITE), \
(casio_stream_seek_t*)(CASIO__SEEK), NULL, NULL}
/* ---
* Stream serial settings ad flags.
* --- */
@ -234,24 +222,6 @@ struct casio_streamattrs_s {
unsigned char casio_streamattrs_cc[CASIO_NCCS];
};
/* This structure will be sent to your `setcomm` callback to set serial
* communication settings.
* And here is the stream timeouts structure: */
struct casio_timeouts_s {
/* Initial read timeout */
unsigned int casio_timeouts_read;
/* In-between bytes read timeout */
unsigned int casio_timeouts_read_bw;
/* Total write timeout */
unsigned int casio_timeouts_write;
};
/* This structure will be sent to your `settm` callback, usually after a state
* change in the communication. Also, all timeouts are in milliseconds (ms). */
/* ---
* SCSI requests.
* --- */
@ -305,21 +275,13 @@ CASIO_BEGIN_DECLS
/* Default stream serial settings utilities. */
CASIO_EXTERN int CASIO_EXPORT casio_make_attrs
OF((casio_streamattrs_t *casio__attrs, const char *casio__raw));
/* List serial devices (platform agnostic). */
typedef void CASIO_EXPORT casio_list_com_t
OF((void *casio__cookie, const char *casio__str));
CASIO_EXTERN int CASIO_EXPORT casio_comlist
OF((casio_list_com_t *casio__callback, void *casio__cookie));
OF((casio_streamattrs_t *casio__attrs, char const *casio__raw));
/* Open and close a stream. */
CASIO_EXTERN int CASIO_EXPORT casio_open_stream
OF((casio_stream_t **casio__stream, casio_openmode_t mode,
void *casio__cookie, const casio_streamfuncs_t *casio__callbacks,
void *casio__cookie, casio_streamfuncs_t const *casio__callbacks,
casio_off_t casio__initial_offset));
CASIO_EXTERN int CASIO_EXPORT casio_close
OF((casio_stream_t *casio__stream));
@ -349,7 +311,7 @@ CASIO_EXTERN int CASIO_EXPORT casio_isseekable
CASIO_EXTERN casio_openmode_t CASIO_EXPORT casio_get_openmode
OF((casio_stream_t *casio__stream));
CASIO_EXTERN const casio_streamfuncs_t* CASIO_EXPORT casio_get_streamfuncs
CASIO_EXTERN casio_streamfuncs_t const* CASIO_EXPORT casio_get_streamfuncs
OF((casio_stream_t *casio__stream));
CASIO_EXTERN void* CASIO_EXPORT casio_get_cookie
@ -357,17 +319,21 @@ CASIO_EXTERN void* CASIO_EXPORT casio_get_cookie
CASIO_EXTERN int CASIO_EXPORT casio_get_lasterr
OF((casio_stream_t *casio__stream));
/* Read and write data from and to a stream. */
/* Read and write data from and to a stream.
* Timeouts are in milliseconds (ms). */
CASIO_EXTERN int CASIO_EXPORT casio_read
OF((casio_stream_t *casio__stream,
void *casio__dest, size_t casio__size));
void *casio__dest, size_t casio__size,
unsigned int casio__timeout));
CASIO_EXTERN int CASIO_EXPORT casio_write
OF((casio_stream_t *casio__stream,
const void *casio__data, size_t casio__size));
void const *casio__data, size_t casio__size,
unsigned int casio__timeout));
CASIO_EXTERN int CASIO_EXPORT casio_write_char
OF((casio_stream_t *casio__stream, int casio__char));
OF((casio_stream_t *casio__stream, int casio__char,
unsigned int casio__timeout));
/* Skip bytes from a stream. */
@ -388,11 +354,6 @@ CASIO_EXTERN int CASIO_EXPORT casio_get_attrs
CASIO_EXTERN int CASIO_EXPORT casio_init_timeouts
OF((casio_stream_t *casio__stream));
CASIO_EXTERN int CASIO_EXPORT casio_set_timeouts
OF((casio_stream_t *casio__stream,
const casio_timeouts_t *casio__timeouts));
CASIO_EXTERN int CASIO_EXPORT casio_get_timeouts
OF((casio_stream_t *casio__stream, casio_timeouts_t *casio__timeouts));
/* Move in a file. */
@ -416,7 +377,7 @@ CASIO_EXTERN int CASIO_EXPORT casio_scsi_request
CASIO_EXTERN int CASIO_EXPORT casio_open_memory
OF((casio_stream_t **casio__stream,
const void *casio__memory, size_t casio__size));
void const *casio__memory, size_t casio__size));
/* Make a stream out of another, with a limit (and empty it). */
@ -436,46 +397,71 @@ CASIO_EXTERN int CASIO_EXPORT casio_open_csum32
* USB and serial stream utilities.
* --- */
/* For platforms whose the utilities aren't built-in, here is a way to add
* your defaults, that will be used with the default functions!
*
* Communication port listing. */
/* Make an iterator to list available serial ports. */
typedef int CASIO_EXPORT casio_comlist_t
OF((casio_list_com_t *casio__callback, void *casio__cookie));
CASIO_EXTERN int CASIO_EXPORT casio_iter_serial
OF((casio_iter_t **casio__iterp));
CASIO_EXTERN int CASIO_EXPORT casio_add_default_comlist
OF((casio_comlist_t *casio__function));
# define casio_next_serial(ITER, NEXTP) \
casio_next((ITER), (void **)(char const **)(NEXTP))
/* Serial communication stream opening. */
/* Replace the default function to list serial devices. */
typedef int casio_opencomstream_t
OF((casio_stream_t **casio__stream, const char *casio__path));
typedef int CASIO_EXPORT casio_iter_serial_t
OF((casio_iter_t **));
CASIO_EXTERN int CASIO_EXPORT casio_add_default_com_stream
OF((casio_opencomstream_t *casio__function));
CASIO_EXTERN int CASIO_EXPORT casio_open_com_stream
OF((casio_stream_t **casio__stream,
const char *casio__path));
CASIO_EXTERN int CASIO_EXPORT casio_set_iter_serial_func
OF((casio_iter_serial_t *casio__func));
/* USB stream opening.
* The `bus` argument is set to -1 if we ought to find the first appropriate
* argument.
* The `address` argument is set to -1 if we ought to find any device on
* the given bus. */
/* Open a serial stream. */
typedef int CASIO_EXPORT casio_openusbstream_t
OF((casio_stream_t **casio__stream,
int casio__bus, int casio__address));
CASIO_EXTERN int CASIO_EXPORT casio_open_serial_stream
OF((casio_stream_t **casio__stream, char const *casio__path,
casio_streamattrs_t const *casio__attributes));
/* Replace the default function to open a serial stream. */
typedef int CASIO_EXPORT casio_open_serial_stream_t
OF((casio_stream_t **casio__stream, char const *casio__path,
casio_streamattrs_t const *casio__attributes));
CASIO_EXTERN int CASIO_EXPORT casio_set_open_serial_stream_func
OF((casio_open_serial_stream_t *casio__func));
/* Make an iterator to list available USB devices. */
# define CASIO_USB_TYPE_UNKNOWN 0 /* Unknown type (not a calculator?) */
# define CASIO_USB_TYPE_LEGACY 1 /* Protocol 7.00 over bulk transfers */
# define CASIO_USB_TYPE_SCSI 2 /* Bulk-Only Transport (SCSI) and
* Protocol 7.00 over commands C0 to C2 */
typedef struct casio_usb_entry_s {
int casio_usb_entry_type; /* one of `CASIO_USB_TYPE_*` */
int casio_usb_entry_bus;
int casio_usb_entry_address;
} casio_usb_entry_t;
CASIO_EXTERN int CASIO_EXPORT casio_iter_usb
OF((casio_iter_t **casio__iterp));
# define casio_next_usb(ITER, NEXTP) \
casio_next((ITER), (void **)(casio_usb_entry_t **)(NEXTP))
/* Open a USB device. */
CASIO_EXTERN int CASIO_EXPORT casio_add_default_usb_stream
OF((casio_openusbstream_t *casio__function));
CASIO_EXTERN int CASIO_EXPORT casio_open_usb_stream
OF((casio_stream_t **casio__stream,
int casio__bus, int casio__address));
/* Replace the default function to open a USB stream. */
typedef int CASIO_EXPORT casio_open_usb_stream_t
OF((casio_stream_t **casio__stream, int casio__bus, int casio__addr));
CASIO_EXTERN int CASIO_EXPORT casio_set_open_usb_stream_func
OF((casio_open_usb_stream_t *casio__func));
CASIO_END_DECLS
CASIO_END_NAMESPACE
# include "builtin.h"
#endif /* LIBCASIO_STREAM_H */

View File

@ -73,11 +73,11 @@ CASIO_BEGIN_DECLS
* and to decode/encode a version. */
CASIO_EXTERN int CASIO_EXPORT casio_check_version
OF((const char *casio__raw));
OF((char const *casio__raw));
CASIO_EXTERN int CASIO_EXPORT casio_decode_version
OF((casio_version_t *casio__version, const char *casio__raw));
OF((casio_version_t *casio__version, char const *casio__raw));
CASIO_EXTERN int CASIO_EXPORT casio_encode_version
OF((char *casio__raw, const casio_version_t *casio__version));
OF((char *casio__raw, casio_version_t const *casio__version));
CASIO_END_DECLS
CASIO_END_NAMESPACE

View File

@ -1,78 +0,0 @@
/* ****************************************************************************
* comlist/builtin/linux.c -- find out Linux serial devices.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#ifdef __linux__
# include <sys/stat.h>
# include <dirent.h>
# include <fcntl.h>
# include <unistd.h>
# include <errno.h>
/**
* casio_comlist_linux:
* List serial devices under Linux.
*
* Links in the /dev/serial/by-id/ should resolve to relative paths, but
* I also managed absolute paths, in case.
*
* @arg callback the callback.
* @arg cookie the cookie.
* @return the error.
*/
int CASIO_EXPORT casio_comlist_linux(casio_list_com_t *callback, void *cookie)
{
char path[PATH_MAX + 1], devname[PATH_MAX + 1], *f, *p;
DIR *d; struct dirent *dr; struct stat st;
ssize_t rl;
/* open the thing */
strcpy(path, "/dev/serial/by-id/");
d = opendir(path); if (!d) return (casio_error_unknown);
/* prepare */
f = strchr(path, 0);
/* read the entries */
while ((dr = readdir(d))) {
/* check type */
strcpy(f, dr->d_name);
if (lstat(path, &st) || (st.st_mode & S_IFMT) != S_IFLNK)
continue;
/* get destination path and send it */
rl = readlink(path, devname, PATH_MAX + 1);
if (rl < 0) continue;
devname[rl] = 0;
if (devname[0] == '/')
(*callback)(cookie, devname);
else {
strcpy(f, devname);
p = realpath(path, devname);
if (!p) continue;
(*callback)(cookie, p);
}
}
/* close the dir and we're done listing */
closedir(d);
return (0);
}
# endif /* __linux__ */

View File

@ -1,61 +0,0 @@
/* ****************************************************************************
* comlist/builtin/macos.c -- find out MacOS/OS X serial devices.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#if defined(__APPLE__) && defined(__MACH__)
# include <dirent.h>
/**
* casio_comlist_macos:
* List serial devices under MacOS/OS X.
*
* @arg callback the callback.
* @arg cookie the cookie.
* @return the error.
*/
int CASIO_EXPORT casio_comlist_macos(casio_list_com_t *callback, void *cookie)
{
char path[PATH_MAX + 1], *f; DIR *d;
struct dirent *dr;
/* prepare the folder */
strcpy(path, "/dev/");
f = strchr(path, 0);
/* open the directory */
d = opendir(path);
if (!d) return (casio_error_unknown);
/* read the entries */
while ((dr = readdir(d))) {
/* check name */
if (strncmp(dr->d_name, "cu.", 3))
continue;
/* copy and set to the user */
strcpy(f, dr->d_name);
(*callback)(cookie, path);
}
/* close the dir and we're done listing */
closedir(d);
return (0);
}
#endif /* __APPLE__, __MACH__ */

View File

@ -1,92 +0,0 @@
/* ****************************************************************************
* comlist/builtin/windows.c -- find out serial devices on MS-Windows.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#ifdef __WINDOWS__
/* only works because I redefined the version at the beginning
* of `internals.h`! */
# include <windows.h>
# include <setupapi.h>
# include <usbiodef.h>
# include <winerror.h>
/**
* casio_comlist_windows:
* List serial devices under MS-Windows.
*
* I'm using the source from Python 3.x's winreg module source and the MSDN
* documentation.
*
* @arg callback the callback to which to send the path.
* @arg cookie the cookie to pass to the callback.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_comlist_windows(casio_list_com_t callback, void *cookie)
{
DWORD werr, i, type, valsize, curval, datasize, curdata;
HKEY hkey; int hkey_open = 0;
char *value = NULL, *data = NULL;
/* read the registry key */
msg((ll_info,
"Opening HKEY_LOCAL_MACHINE\\HARDWARE\\DEVICEMAP\\SERIALCOMM"));
werr = RegOpenKey(HKEY_LOCAL_MACHINE,
"HARDWARE\\DEVICEMAP\\SERIALCOMM", &hkey);
if (werr) goto fail;
hkey_open = 1;
/* prepare */
msg((ll_info, "Allocating enough space"));
valsize = 1024; datasize = 1024; /* I DON'T CARE IT WORKS LALALA */
if (!(value = casio_alloc(valsize, 1))
|| !(data = casio_alloc(datasize, 1)))
goto fail;
/* enumerate values */
msg((ll_info, "Enumerating values"));
curval = valsize;
curdata = datasize;
for (i = 0; (werr = RegEnumValue(hkey, i, value, &curval, NULL,
&type, (BYTE*)data, &curdata)) != ERROR_NO_MORE_ITEMS; i++) {
if (type != REG_SZ)
continue;
if (werr == ERROR_MORE_DATA) {
msg((ll_error, "data not big enough, o shit waddap"));
goto fail;
}
(*callback)(cookie, data);
curval = valsize;
curdata = datasize;
}
/* error is `ERROR_MORE_DATA`, o ship shaddap */
werr = 0;
fail:
ifmsg(werr, (ll_error, "Got error %08lu", werr))
/* Free, close the key and return ! */
casio_free(value);
casio_free(data);
if (hkey_open)
RegCloseKey(hkey);
return (werr ? casio_error_unknown : 0);
}
#endif /* __WINDOWS__ */

View File

@ -1,84 +0,0 @@
/* ****************************************************************************
* comlist/builtin.c -- find out serial devices.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../internals.h"
#define NUM 5
/* Correspondance type. */
struct corresp {
int _valid;
casio_comlist_t *_comlist;
};
/* List of com listing functions. */
CASIO_LOCAL struct corresp comlists[NUM + 1] = {
#if defined(__linux__)
{1, casio_comlist_linux},
#elif defined(__WINDOWS__)
{1, casio_comlist_windows},
#elif defined(__APPLE__) && defined(__MACH__)
{1, casio_comlist_macos},
#endif
{0, NULL}
};
/**
* casio_add_default_comlist:
* Add a default `comlist` function.
*
* @arg callback the callback.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_add_default_comlist(casio_comlist_t *function)
{
struct corresp *c; int num;
for (c = comlists, num = NUM; c->_valid && num; c++, num--);
if (!num) return (casio_error_op);
c->_valid = 1;
c->_comlist = function;
return (0);
}
/**
* casio_comlist:
* List the communication ports.
*
* @arg callback the callback.
* @arg cookie the cookie.
* @return the error (if any).
*/
int CASIO_EXPORT casio_comlist(casio_list_com_t callback, void *cookie)
{
int err; struct corresp *c = comlists;
if (!c->_valid)
return (casio_error_op);
for (; c->_valid; c++) {
err = (*c->_comlist)(callback, cookie);
if (!err) return (0);
if (err != casio_error_nocalc)
return (err);
}
return (casio_error_nocalc);
}

View File

@ -39,7 +39,9 @@ const char* CASIO_EXPORT casio_error_strings[128] = {
"a timeout has occurred",
"could not get access to the device",
"an end of file event has occured",
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
"a SCSI operation on the stream has failed",
"a USB operation on the stream has failed",
NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,

View File

@ -28,12 +28,12 @@
/* Read from a stream. */
# define READ(CASIO__TO, CASIO__SZ) /* normal read */ { \
int READ_err = casio_read(buffer, (CASIO__TO), (CASIO__SZ)); \
int READ_err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0); \
if (READ_err) return (READ_err); }
# define FREAD(CASIO__TO, CASIO__SZ) /* fail-less read */ \
err = casio_read(buffer, (CASIO__TO), (CASIO__SZ));
err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0);
# define GREAD(CASIO__TO, CASIO__SZ) /* read with goto fail */ \
if ((err = casio_read(buffer, (CASIO__TO), (CASIO__SZ)))) \
if ((err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0))) \
goto fail;
/* Read using size of the object. */

View File

@ -17,7 +17,7 @@
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LOCAL_INTERNALS_H
# define LOCAL_INTERNALS_H 1
# define LOCAL_INTERNALS_H 2018051701
# define _DEFAULT_SOURCE /* XXX: glibc hacking */
# define _POSIX_C_SOURCE 199309L
# include <libcasio.h>
@ -29,13 +29,19 @@
# include "utils/endian.h"
# include "log/log.h"
/* ---
* Platform-specific stuff.
* --- */
/* MS-Windows stuff */
# if (defined(_WIN16) || defined(_WIN32) || defined(_WIN64)) \
&& !defined(__WINDOWS__)
# define __WINDOWS__
# endif
/* Standard library macros. */
# ifndef min
# define min(CASIO__A, CASIO__B) \
((CASIO__A) < (CASIO__B) ? (CASIO__A) : (CASIO__B))
@ -49,6 +55,41 @@
((CASIO__A) < 0 ? -(CASIO__A) : (CASIO__A))
# endif
/* ---
* Built-in streams.
* --- */
/* Make a stream using the standard FILE interface. */
# ifndef LIBCASIO_DISABLED_FILE
CASIO_EXTERN int CASIO_EXPORT casio_open_stream_file
OF((casio_stream_t **casio__stream,
FILE *casio__readstream, FILE *casio__writestream,
int casio__close_readstream, int casio__close_writestream));
# endif
/* ---
* Built-in filesystems.
* --- */
/* Make a POSIX filesystem interface. */
# ifndef LIBCASIO_DISABLED_STREAMS
CASIO_EXTERN int CASIO_EXPORT casio_open_posix_fs
OF((casio_fs_t **casio__filesystem));
# endif
/* Make a Windows API filesystem interface. */
# ifndef LIBCASIO_DISABLED_WINDOWS
CASIO_EXTERN int CASIO_EXPORT casio_open_windows_fs
OF((casio_fs_t **casio__filesystem));
# endif
/* ---
* Various.
* --- */
/* Checksum. */
extern int casio_checksum_cas OF((void *casio__mem,

View File

@ -1,5 +1,5 @@
/* ****************************************************************************
* utils/iter.c -- iterator internals.
* iter/iter.c -- iterator internals.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
@ -16,7 +16,7 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include <libcasio.h>
#include "../internals.h"
/* Internal structure of an iterator. */

96
lib/iter/super.c Normal file
View File

@ -0,0 +1,96 @@
/* ****************************************************************************
* iter/super.c -- super-iterator, for super-iterating.
* Copyright (C) 2018 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../internals.h"
typedef struct {
int i, len;
casio_iter_t *its[2];
} supercookie_t;
/* `next_super()`: next element from the super iterator. */
CASIO_LOCAL int next_super(supercookie_t *cookie, void **ptr)
{
int err;
if (cookie->i == cookie->len)
return (casio_error_iter);
while (cookie->i < cookie->len - 1) {
if ((err = casio_next(cookie->its[cookie->i], ptr))
!= casio_error_iter)
return (err);
casio_end(cookie->its[cookie->i++]);
}
if ((err = casio_next(cookie->its[cookie->i], ptr)) != casio_error_iter)
return (err);
casio_end(cookie->its[cookie->i++]);
return (casio_error_iter);
}
/* `end_super()`: end the super-iterator. */
CASIO_LOCAL void end_super(supercookie_t *cookie)
{
int i;
for (i = cookie->i; i < cookie->len; i++)
casio_end(cookie->its[i]);
free(cookie);
}
/* Callbacks. */
CASIO_LOCAL casio_iter_funcs_t const super_funcs = {
(casio_next_t *)next_super,
NULL,
(casio_end_t *)end_super
};
/**
* casio_combine_iterator:
* Make a super iterator.
*
* @arg iterp the super-iterator to create.
* @arg first the first iterator to put into the super-iterator.
* @arg second the second one.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_combine_iterators(casio_iter_t **iterp,
casio_iter_t *first, casio_iter_t *second)
{
supercookie_t *cookie;
if (!(cookie = malloc(sizeof(supercookie_t)))) {
casio_end(first);
casio_end(second);
return (casio_error_alloc);
}
cookie->len = 2;
cookie->i = 0;
cookie->its[0] = first;
cookie->its[1] = second;
return (casio_iter(iterp, cookie, &super_funcs));
}

View File

@ -30,12 +30,11 @@
* @arg h the handle to create
* @arg flags the flags.
* @arg stream the stream to use.
* @arg settings the stream settings to use.
* @return the error (0 if ok)
*/
int CASIO_EXPORT casio_open_link(casio_link_t **h, unsigned long flags,
casio_stream_t *stream, const casio_streamattrs_t *settings)
casio_stream_t *stream)
{
int err = 0;
casio_link_t *handle;
@ -77,14 +76,6 @@ int CASIO_EXPORT casio_open_link(casio_link_t **h, unsigned long flags,
msg((ll_info, "[Options] Terminate: %s",
flags & CASIO_LINKFLAG_TERM ? "yes" : "no"));
/* Set communication properties. */
msg((ll_info, "Initializing stream settings."));
if (!settings)
casio_init_attrs(handle->casio_link_stream);
else
casio_set_attrs(handle->casio_link_stream, settings);
/* If active, start. */
err = casio_seven_start(handle);

View File

@ -19,7 +19,7 @@
#include "../link.h"
/**
* casio_open_com:
* casio_open_serial:
* Open a serial communication.
*
* @arg handle the link handle to make.
@ -29,8 +29,8 @@
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_open_com(casio_link_t **handle, unsigned long flags,
const char *path, const casio_streamattrs_t *attrs)
int CASIO_EXPORT casio_open_serial(casio_link_t **handle, unsigned long flags,
char const *path, casio_streamattrs_t const *attrs)
{
int err, failed = 0, tries = 3; casio_stream_t *stream;
@ -43,7 +43,7 @@ int CASIO_EXPORT casio_open_com(casio_link_t **handle, unsigned long flags,
casio_sleep(1000);
}
err = casio_open_com_stream(&stream, path);
err = casio_open_serial_stream(&stream, path, attrs);
if (err == casio_error_op)
return (casio_error_nocalc);
if (!err)
@ -57,7 +57,7 @@ int CASIO_EXPORT casio_open_com(casio_link_t **handle, unsigned long flags,
failed = 1;
}
err = casio_open_link(handle, flags, stream, attrs);
err = casio_open_link(handle, flags, stream);
if (err)
return (err);

View File

@ -77,9 +77,5 @@ int CASIO_EXPORT casio_open_usb(casio_link_t **handle, unsigned long flags,
/* Open the link based on the stream. */
err = casio_open_link(handle, flags, stream, NULL);
if (err)
return (err);
return (0);
return (casio_open_link(handle, flags, stream));
}

View File

@ -64,8 +64,8 @@ int CASIO_EXPORT casio_seven_send_buffer(casio_link_t *handle,
/* Read the big block. */
toread = min(BUFSIZE, size);
err = casio_read(buffer, buf + 8, toread);
if (err) return (casio_error_noread);
if ((err = casio_read(buffer, buf + 8, toread, 0)))
return (casio_error_noread);
size -= toread;
/* Send each block. */
@ -165,11 +165,15 @@ int CASIO_EXPORT casio_seven_get_buffer(casio_link_t *handle,
msg((ll_info, "buffer too full, should be emptied"));
/* Empty the buffer in the stream. */
buf_err = casio_write(buffer, buf, ps);
if (buf_err) { err = casio_error_nowrite; goto fail; }
if ((buf_err = casio_write(buffer, buf, ps, 0))) {
err = casio_error_nowrite;
goto fail;
}
/* Reset the pointer. */
p = buf; ps = 0;
p = buf;
ps = 0;
}
}

View File

@ -51,16 +51,19 @@ typedef struct {
* @arg cookie the cookie.
* @arg data the data to read.
* @arg size the size of the data to read.
* @arg timeout the timeout (ignored).
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_seven_data_read(seven_data_cookie_t *cookie,
unsigned char *data, size_t size)
unsigned char *data, size_t size, unsigned int timeout)
{
int err; size_t tocopy;
casio_link_t *handle = cookie->_link;
unsigned int lastsize;
(void)timeout;
/* Check if the stream is faulty. */
if (cookie->_faulty)
return (casio_error_noread);
@ -139,15 +142,18 @@ fail:
* @arg cookie the cookie.
* @arg data the data to write.
* @arg size the size of the data to write.
* @arg timeout the timeout (ignored).
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_seven_data_write(seven_data_cookie_t *cookie,
const unsigned char *data, size_t size)
const unsigned char *data, size_t size, unsigned int timeout)
{
int err; size_t tocopy, lastlimit;
casio_link_t *handle = cookie->_link;
(void)timeout;
/* Check if the stream is faulty, or if we have already finished. */
if (cookie->_faulty)
return (casio_error_nowrite);
@ -279,11 +285,11 @@ CASIO_LOCAL int casio_seven_data_close(seven_data_cookie_t *cookie)
* go directly to the end. */
memset(zeroes, 0, BUFSIZE);
for (; left >= BUFSIZE; left -= BUFSIZE) {
if ((err = casio_seven_data_write(cookie, zeroes, BUFSIZE)))
if ((err = casio_seven_data_write(cookie, zeroes, BUFSIZE, 0)))
goto fail;
}
err = casio_seven_data_write(cookie, zeroes, left);
err = casio_seven_data_write(cookie, zeroes, left, 0);
}
err = 0;
@ -296,9 +302,13 @@ fail:
* Opening functions.
* --- */
CASIO_LOCAL const casio_streamfuncs_t seven_data_callbacks =
casio_stream_callbacks_for_virtual(casio_seven_data_close,
casio_seven_data_read, casio_seven_data_write, NULL);
CASIO_LOCAL const casio_streamfuncs_t seven_data_callbacks = {
(casio_stream_close_t *)casio_seven_data_close,
(casio_stream_read_t *)casio_seven_data_read,
(casio_stream_write_t *)casio_seven_data_write,
NULL, NULL, NULL, NULL, NULL
};
/**
* casio_seven_open_data_stream:

View File

@ -23,41 +23,45 @@
* Raw layout of an extended ack data.
* --- */
/* `hwid`: hardware identifier (ASCII);
* `cpuid`: processor identifier (ASCII);
*
* `preprog_rom_capacity`: preprogrammed ROM capacity (ASCII-DEC, KiB);
* `flash_rom_capacity`: flash ROM capacity (ASCII-DEC, KiB);
* `ram_capacity`: RAM capacity (ASCII-DEC, KiB);
*
* `preprog_rom_version`: preprogrammed ROM version.
* `bootcode_version`: bootcode version.
* `bootcode_offset`: bootcode offset (ASCII-HEX);
* `bootcode_size`: bootcode size (ASCII-HEX, KiB);
* `os_version`: OS version;
* `os_offset`: OS offset;
* `os_size`: OS size (ASCII-HEX, KiB);
*
* `protocol_version`: protocol version (x.xx, generally "7.00");
* `product_id`: product ID;
* `username`: name set by the user in SYSTEM (Oxffs if in exam mode).
*
* Versions are coded as "xx.xx.xxxx" + 0xff bytes. */
typedef struct {
/* hardware identifier - ASCII */
unsigned char hwid[8];
/* processor identifier - ASCII */
unsigned char cpuid[16];
/* preprogrammed ROM capacity - ASCII-dec (Ko) */
unsigned char preprog_rom_capacity[8];
/* flash ROM capacity - ASCII-dec (Ko) */
unsigned char flash_rom_capacity[8];
/* RAM capacity - ASCII-dec (Ko) */
unsigned char ram_capacity[8];
/* preprogrammed ROM version - "xx.xx.xxxx" + 0xff bytes */
unsigned char preprog_rom_version[16];
/* bootcode version - "xx.xx.xxxx" + 0xff bytes */
unsigned char bootcode_version[16];
/* bootcode offset - ASCII-hex */
unsigned char bootcode_offset[8];
/* bootcode size - ASCII-hex (Ko) */
unsigned char bootcode_size[8];
/* OS version - "xx.xx.xxxx" + 0xff bytes */
unsigned char os_version[16];
/* OS offset - ASCII-hex */
unsigned char os_offset[8];
/* OS size - ASCII-hex (Ko) */
unsigned char os_size[8];
/* protocol version - "x.xx" */
unsigned char protocol_version[4];
/* product ID */
unsigned char product_id[16];
/* name set by user in SYSTEM (if not in exam mode) */
unsigned char username[16];
} packetdata_ackext_t;
@ -75,7 +79,8 @@ typedef struct {
* @arg data the raw version data ("xx.xx.xx" + type)
*/
CASIO_LOCAL void version_of_string(casio_version_t *ver, const unsigned char *data)
CASIO_LOCAL void version_of_string(casio_version_t *ver,
unsigned char const *data)
{
casio_decode_version(ver, (const char*)data);
}
@ -89,9 +94,9 @@ CASIO_LOCAL void version_of_string(casio_version_t *ver, const unsigned char *da
*/
CASIO_LOCAL void string_of_version(unsigned char *data,
const casio_version_t *ver)
casio_version_t const *ver)
{
casio_encode_version((char*)data, ver);
casio_encode_version((char *)data, ver);
memset(&data[10], '\xFF', 6);
}
@ -113,16 +118,18 @@ int CASIO_EXPORT casio_seven_send_eack(casio_link_t *handle,
{
packetdata_ackext_t raw;
/* initialize the structure with 0xFFs */
/* Initialize the structure with 0xFFs. */
memset(&raw, 0xFF, sizeof(packetdata_ackext_t));
/* put in the structure */
/* Put in the structure. */
memcpy(raw.hwid, info->casio_link_info_hwid,
strnlen(info->casio_link_info_hwid, 8));
memcpy(raw.cpuid, info->casio_link_info_cpuid,
strnlen(info->casio_link_info_cpuid, 16));
if (!(info->casio_link_info_wiped & casio_link_info_wiped_preprog)) {
if (info->casio_link_info_flags & casio_link_info_flag_preprog) {
casio_putascii(raw.preprog_rom_capacity,
info->casio_link_info_rom_capacity, 8);
string_of_version(raw.preprog_rom_version,
@ -134,7 +141,7 @@ int CASIO_EXPORT casio_seven_send_eack(casio_link_t *handle,
casio_putascii(raw.ram_capacity,
casio_gethex(info->casio_link_info_ram_capacity / 1024), 8);
if (!(info->casio_link_info_wiped & casio_link_info_wiped_bootcode)) {
if (info->casio_link_info_flags & casio_link_info_flag_bootcode) {
string_of_version(raw.bootcode_version,
&info->casio_link_info_bootcode_version);
casio_putascii(raw.bootcode_offset,
@ -143,7 +150,7 @@ int CASIO_EXPORT casio_seven_send_eack(casio_link_t *handle,
casio_gethex(info->casio_link_info_bootcode_size / 1024), 8);
}
if (!(info->casio_link_info_wiped & casio_link_info_wiped_os)) {
if (info->casio_link_info_flags & casio_link_info_flag_os) {
string_of_version(raw.os_version, &info->casio_link_info_os_version);
casio_putascii(raw.os_offset, info->casio_link_info_os_offset, 8);
casio_putascii(raw.os_size,
@ -156,7 +163,8 @@ int CASIO_EXPORT casio_seven_send_eack(casio_link_t *handle,
memcpy(raw.username, info->casio_link_info_username,
strnlen(info->casio_link_info_username, 16));
/* send the packet */
/* Send the packet. */
return (casio_seven_send_ext(handle, casio_seven_type_ack, 0x02, &raw,
sizeof(packetdata_ackext_t), 1));
}
@ -201,94 +209,97 @@ int CASIO_EXPORT casio_seven_decode_ack(casio_link_t *handle,
casio_link_info_t *info = &packet->casio_seven_packet_info;
const packetdata_ackext_t *d = (const void*)data;
/* check the data size */
if (data_size != sizeof(packetdata_ackext_t)) return (1);
info->casio_link_info_wiped = 0;
/* Check the data size. */
/* log */
msg((ll_info, "ack packet is extended"));
/* hardware identifier */
if (data_size != sizeof(packetdata_ackext_t)) {
msg((ll_warn, "eack extension is of invalid size?"));
return (1);
}
info->casio_link_info_flags = 0;
/* Hardware identifier, processor identifier. */
cpy_string(info->casio_link_info_hwid, (const char*)d->hwid, 8);
msg((ll_info, "hardware identifier is '%s'", info->casio_link_info_hwid));
/* processor identifier */
cpy_string(info->casio_link_info_cpuid, (const char*)d->cpuid, 16);
msg((ll_info, "hardware identifier is '%s'", info->casio_link_info_hwid));
msg((ll_info, "cpu identifier is '%s'", info->casio_link_info_cpuid));
/* preprogrammed ROM information is wiped */
if (d->preprog_rom_version[2] == 0xFF)
info->casio_link_info_wiped |= casio_link_info_wiped_preprog;
ifmsg(info->casio_link_info_wiped & casio_link_info_wiped_preprog,
(ll_info, "Preprogrammed ROM information looks wiped out!"))
elsemsg((ll_info, "Preprogrammed ROM version is %.10s",
d->preprog_rom_version))
/* Preprogrammed ROM information (valid, capacity, version). */
/* preprogrammed ROM capacity */
info->casio_link_info_rom_capacity =
casio_getascii(d->preprog_rom_capacity, 8) * 1000;
msg((ll_info, "preprogrammed ROM capacity is %luo",
info->casio_link_info_rom_capacity));
/* preprogrammed ROM version */
version_of_string(&info->casio_link_info_rom_version,
d->preprog_rom_version);
/* flash ROM capacity */
if (d->preprog_rom_version[2] != 0xFF) {
info->casio_link_info_flags |= casio_link_info_flag_preprog;
msg((ll_info, "preprogrammed ROM capacity is %luo",
info->casio_link_info_rom_capacity));
msg((ll_info, "Preprogrammed ROM version is %.10s",
d->preprog_rom_version));
} elsemsg((ll_info, "Preprogrammed ROM information looks wiped out!"))
/* Flash ROM and RAM capacities. */
info->casio_link_info_flash_rom_capacity =
casio_getdec(casio_getascii(d->flash_rom_capacity, 8)) * 1024;
msg((ll_info, "flash ROM capacity is %luKiB",
info->casio_link_info_flash_rom_capacity / 1024));
/* RAM capacity */
info->casio_link_info_ram_capacity =
casio_getdec(casio_getascii(d->ram_capacity, 8)) * 1024;
msg((ll_info, "flash ROM capacity is %luKiB",
info->casio_link_info_flash_rom_capacity / 1024));
msg((ll_info, "RAM capacity is %luKiB",
info->casio_link_info_ram_capacity / 1024));
/* bootcode information is wiped */
if (d->bootcode_version[2] == 0xFF)
info->casio_link_info_wiped |= casio_link_info_wiped_bootcode;
ifmsg(info->casio_link_info_wiped & casio_link_info_wiped_bootcode,
(ll_info, "Bootcode information looks wiped out!"))
elsemsg((ll_info, "Bootcode version is %.10s", d->bootcode_version))
/* Bootcode information (valid, offset, size, version). */
/* bootcode version */
version_of_string(&info->casio_link_info_bootcode_version,
d->bootcode_version);
/* bootcode offset */
info->casio_link_info_bootcode_offset =
casio_getascii(d->bootcode_offset, 8);
msg((ll_info, "bootcode offset is 0x%08lX",
info->casio_link_info_bootcode_offset));
/* bootcode size */
info->casio_link_info_bootcode_size =
casio_getdec(casio_getascii(d->bootcode_size, 8)) * 1024;
msg((ll_info, "bootcode size is %luKiB",
info->casio_link_info_bootcode_size / 1024));
/* OS information is wiped */
if (d->os_version[2] == 0xFF)
info->casio_link_info_wiped |= casio_link_info_wiped_os;
ifmsg(info->casio_link_info_wiped & casio_link_info_wiped_os,
(ll_info, "OS information looks wiped out!"))
elsemsg((ll_info, "OS version is %.10s", d->os_version))
if (d->bootcode_version[2] != 0xFF) {
info->casio_link_info_flags |= casio_link_info_flag_bootcode;
msg((ll_info, "Bootcode version is %.10s", d->bootcode_version));
msg((ll_info, "bootcode offset is 0x%08lX",
info->casio_link_info_bootcode_offset));
msg((ll_info, "bootcode size is %luKiB",
info->casio_link_info_bootcode_size / 1024));
} elsemsg((ll_info, "Bootcode information looks wiped out!"))
/* OS information (valid, offset, size, version). */
/* OS version */
version_of_string(&info->casio_link_info_os_version, d->os_version);
/* OS offset */
info->casio_link_info_os_offset = casio_getascii(d->os_offset, 8);
msg((ll_info, "OS offset is 0x%08lX" , info->casio_link_info_os_offset));
/* OS size */
info->casio_link_info_os_size =
casio_getdec(casio_getascii(d->os_size, 8)) * 1024;
msg((ll_info, "OS size is %luKiB", info->casio_link_info_os_size / 1024));
/* product ID */
if (d->os_version[2] != 0xFF) {
info->casio_link_info_flags |= casio_link_info_flag_os;
msg((ll_info, "OS version is %.10s", d->os_version));
msg((ll_info, "OS offset is 0x%08lX" ,
info->casio_link_info_os_offset));
msg((ll_info, "OS size is %luKiB",
info->casio_link_info_os_size / 1024));
} elsemsg((ll_info, "OS information looks wiped out!"))
/* Product ID and username. */
cpy_string(info->casio_link_info_product_id,
(const char*)d->product_id, 16);
msg((ll_info, "product ID is %s", info->casio_link_info_product_id));
/* username */
cpy_string(info->casio_link_info_username, (const char*)d->username, 16);
msg((ll_info, "product ID is %s", info->casio_link_info_product_id));
msg((ll_info, "username is %s", info->casio_link_info_username));
/* no error */
return (0);
}

View File

@ -176,7 +176,7 @@ CASIO_LOCAL const char *gettermstring(casio_seven_term_t code)
#define buffer handle->casio_link_recv_buffer
#define COMPLETE_PACKET(N) { \
int COMP_PACKET_err = casio_read(handle->casio_link_stream, \
&buffer[received], (size_t)(N)); \
&buffer[received], (size_t)(N), 0); \
received += (N); if (COMP_PACKET_err) return (COMP_PACKET_err); }
CASIO_LOCAL int casio_seven_decode(casio_link_t *handle, int scralign)

View File

@ -84,10 +84,14 @@ typedef struct {
* --- */
CASIO_LOCAL int seven_scsi_read(seven_scsi_cookie_t *cookie,
unsigned char *buffer, size_t size)
unsigned char *buffer, size_t size, unsigned int timeout)
{
casio_scsi_t scsi; int err;
/* FIXME: use the timeout! */
(void)timeout;
/* Empty what's already in the buffer. */
if (cookie->left) {
@ -197,74 +201,105 @@ CASIO_LOCAL int seven_scsi_read(seven_scsi_cookie_t *cookie,
}
CASIO_LOCAL int seven_scsi_write(seven_scsi_cookie_t *cookie,
unsigned char const *buffer, size_t size)
unsigned char const *buffer, size_t size, unsigned int timeout)
{
casio_scsi_t scsi;
casio_timer_t *timer = NULL;
unsigned long spent;
int err;
do {
casio_uint16_t activity;
if (timeout) {
if ((err = casio_get_timer(&timer)))
return (err);
}
/* Polling loop. */
while (size) {
do {
casio_uint16_t activity;
casio_uint16_t to_send;
while (1) {
casio_uint8_t poll_command[16] = {0xC0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
casio_uint8_t poll_data[16];
/* Polling loop. */
msg((ll_info, "Polling the activity using command C0..."));
while (1) {
casio_uint8_t poll_command[16] = {0xC0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
casio_uint8_t poll_data[16];
/* Poll to check the activity. */
msg((ll_info, "Polling the activity using command C0..."));
scsi.casio_scsi_cmd = poll_command;
scsi.casio_scsi_cmd_len = 16;
scsi.casio_scsi_direction = CASIO_SCSI_DIREC_FROM_DEV;
scsi.casio_scsi_data = poll_data;
scsi.casio_scsi_data_len = 16;
/* Poll to check the activity. */
if ((err = casio_scsi_request(cookie->stream, &scsi)))
return (err);
scsi.casio_scsi_cmd = poll_command;
scsi.casio_scsi_cmd_len = 16;
scsi.casio_scsi_direction = CASIO_SCSI_DIREC_FROM_DEV;
scsi.casio_scsi_data = poll_data;
scsi.casio_scsi_data_len = 16;
#if 0
activity = (poll_data[10] << 8) | poll_data[11];
if ((err = casio_scsi_request(cookie->stream, &scsi))) {
casio_free_timer(timer);
return (err);
}
if (activity == 0x1000) {
/* The calculator is busy.
* FIXME: delay and check the timeout!! */
/* Get the number of bytes left on the receiving buffer
* on the calculator. */
continue;
activity = (poll_data[10] << 8) | poll_data[11];
if (!activity) {
/* The calculator is busy.
* We ought to check the timeout and delay. */
if (timeout) {
if (!casio_get_spent_time(timer, &spent)
|| spent > (unsigned long)timeout) {
casio_free_timer(timer);
return (casio_error_time);
}
spent = (unsigned long)timeout - spent;
if (spent > 500)
spent = 500;
} else
spent = 500;
casio_sleep(spent);
continue;
}
to_send = (size_t)activity;
if ((size_t)to_send > size)
to_send = (casio_uint16_t)size;
break;
}
#endif
break;
}
/* Actually send the data. */
/* Actually send some of the data. */
{
casio_uint8_t send_command[16] = {0xC2,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
{
casio_uint16_t to_send = (size > 0xFFFF) ? 0xFFFF : size;
casio_uint8_t send_command[16] = {0xC2,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
msg((ll_info, "Sending the data using command C2..."));
msg((ll_info, "Sending the data using command C2..."));
send_command[6] = (to_send >> 8) & 0xFF;
send_command[7] = to_send & 0xFF;
send_command[6] = (to_send >> 8) & 0xFF;
send_command[7] = to_send & 0xFF;
scsi.casio_scsi_cmd = send_command;
scsi.casio_scsi_cmd_len = 16;
scsi.casio_scsi_direction = CASIO_SCSI_DIREC_TO_DEV;
scsi.casio_scsi_data = (casio_uint8_t *)buffer;
scsi.casio_scsi_data_len = to_send;
scsi.casio_scsi_cmd = send_command;
scsi.casio_scsi_cmd_len = 16;
scsi.casio_scsi_direction = CASIO_SCSI_DIREC_TO_DEV;
scsi.casio_scsi_data = (casio_uint8_t *)buffer;
scsi.casio_scsi_data_len = to_send;
if ((err = casio_scsi_request(cookie->stream, &scsi))) {
casio_free_timer(timer);
return (err);
}
if ((err = casio_scsi_request(cookie->stream, &scsi)))
return (err);
buffer += to_send;
size -= to_send;
}
} while (size);
buffer += to_send;
size -= to_send;
}
} while (size);
}
casio_free_timer(timer);
return (0);
}
@ -293,12 +328,11 @@ CASIO_LOCAL int seven_scsi_close(seven_scsi_cookie_t *cookie)
CASIO_LOCAL casio_streamfuncs_t seven_scsi_funcs = {
(casio_stream_close_t *)seven_scsi_close,
NULL,
(casio_stream_read_t *)seven_scsi_read,
(casio_stream_write_t *)seven_scsi_write,
NULL,
NULL,
(casio_stream_scsi_t *)seven_scsi_request
NULL, NULL,
(casio_stream_scsi_t *)seven_scsi_request,
NULL, NULL
};
int CASIO_EXPORT casio_open_seven_scsi(casio_stream_t **streamp,

View File

@ -25,6 +25,7 @@
casio_checksum_sub(&((char*)(BUF))[1], (SIZE) - 3, 0)
/* Internal macros. */
#define buffer \
handle->casio_link_send_buffers[handle->casio_link_flags \
& casio_linkflag_sendalt]
@ -91,7 +92,7 @@ CASIO_LOCAL int casio_seven_send_buf(casio_link_t *handle,
}
/* send prepared packet */
err = casio_write(handle->casio_link_stream, buf, bufsize);
err = casio_write(handle->casio_link_stream, buf, bufsize, 0);
if (err) return (err);
/* set wasreset for logging */

View File

@ -42,10 +42,9 @@ CASIO_LOCAL int CASIO_EXPORT next_log(const char ***cookie, const char **level)
/* `end_log_iter()`: end the iteration log. */
CASIO_LOCAL int CASIO_EXPORT end_log_iter(const char ***cookie)
CASIO_LOCAL void CASIO_EXPORT end_log_iter(char const ***cookie)
{
free(cookie);
return (0);
}
/* Functions. */

View File

@ -27,12 +27,12 @@
/* Read from a stream. */
# define READ(CASIO__TO, CASIO__SZ) /* normal read */ { \
int READ_err = casio_read(buffer, (CASIO__TO), (CASIO__SZ)); \
int READ_err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0); \
if (READ_err) return (READ_err); }
# define FREAD(CASIO__TO, CASIO__SZ) /* fail-less read */ \
err = casio_read(buffer, (CASIO__TO), (CASIO__SZ));
err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0);
# define GREAD(CASIO__TO, CASIO__SZ) /* read with goto fail */ \
if ((err = casio_read(buffer, (CASIO__TO), (CASIO__SZ)))) \
if ((err = casio_read(buffer, (CASIO__TO), (CASIO__SZ), 0))) \
goto fail;
/* Read using size of the object. */
@ -54,7 +54,7 @@
/* Write. */
# define WRITE(CASIO__BUF, CASIO__SZ) { \
int WRITE_err = casio_write(buffer, (CASIO__BUF), (CASIO__SZ)); \
int WRITE_err = casio_write(buffer, (CASIO__BUF), (CASIO__SZ), 0); \
if (WRITE_err) return (WRITE_err); }
# define DWRITE(CASIO__OBJECT) \
WRITE(&(CASIO__OBJECT), sizeof(CASIO__OBJECT))

View File

@ -30,7 +30,7 @@
*/
int CASIO_EXPORT casio_encode_picture(void *vraw,
const casio_pixel_t **pixels, casio_pictureformat_t format,
casio_pixel_t const * const *pixels, casio_pictureformat_t format,
unsigned int width, unsigned int height)
{
int msk;

View File

@ -33,9 +33,12 @@
int CASIO_EXPORT casio_make_attrs(casio_streamattrs_t *attrs, const char *raw)
{
unsigned int speed; char par; int stop;
unsigned int speed;
char par;
int stop;
/* Check if we just want to initialize. */
/* check if we just want to initialize */
if (!raw) {
memset(attrs, 0, sizeof(casio_streamattrs_t)); /* ABI XXX */
attrs->casio_streamattrs_flags =
@ -44,7 +47,8 @@ int CASIO_EXPORT casio_make_attrs(casio_streamattrs_t *attrs, const char *raw)
return (0);
}
/* extract data from the string */
/* Extract data from the string. */
if (sscanf(raw, "%u%c%d", &speed, &par, &stop) < 3
|| (par != 'N' && par != 'E' && par != 'O')
|| (stop != 1 && stop != 2)) {
@ -52,22 +56,40 @@ int CASIO_EXPORT casio_make_attrs(casio_streamattrs_t *attrs, const char *raw)
return (casio_error_op);
}
/* get the speed */
/* Get the speed. */
switch (speed) {
case 1200: speed = CASIO_B1200; break;
case 2400: speed = CASIO_B2400; break;
case 4800: speed = CASIO_B4800; break;
case 9600: speed = CASIO_B9600; break;
case 19200: speed = CASIO_B19200; break;
case 38400: speed = CASIO_B38400; break;
case 57600: speed = CASIO_B57600; break;
case 115200: speed = CASIO_B115200; break;
case 1200:
speed = CASIO_B1200;
break;
case 2400:
speed = CASIO_B2400;
break;
case 4800:
speed = CASIO_B4800;
break;
case 9600:
speed = CASIO_B9600;
break;
case 19200:
speed = CASIO_B19200;
break;
case 38400:
speed = CASIO_B38400;
break;
case 57600:
speed = CASIO_B57600;
break;
case 115200:
speed = CASIO_B115200;
break;
default:
msg((ll_error, "%u isn't a valid speed!", speed));
return (casio_error_op);
}
/* set the settings */
/* Set the settings. */
casio_make_attrs(attrs, NULL);
attrs->casio_streamattrs_speed = speed;
attrs->casio_streamattrs_flags &= ~(CASIO_TWOSTOPBITS | CASIO_PARMASK);
@ -76,6 +98,7 @@ int CASIO_EXPORT casio_make_attrs(casio_streamattrs_t *attrs, const char *raw)
attrs->casio_streamattrs_flags |= par == 'N' ? CASIO_PARDIS
: par == 'E' ? CASIO_PARENB | CASIO_PAREVEN
: CASIO_PARENB | CASIO_PARODD;
return (0);
}
@ -93,18 +116,24 @@ int CASIO_EXPORT casio_make_attrs(casio_streamattrs_t *attrs, const char *raw)
int CASIO_EXPORT casio_init_attrs(casio_stream_t *stream)
{
int err; casio_stream_setattrs_t *s;
int err;
casio_stream_setattrs_t *s;
casio_streamattrs_t attrs;
if (!stream) return (casio_error_op);
s = getcb(stream, setattrs);
if (!s) return (casio_error_op);
if (!stream
|| !(s = stream->casio_stream_callbacks.casio_streamfuncs_setattrs))
return (casio_error_op);
casio_make_attrs(&attrs, NULL);
err = (*s)(stream->casio_stream_cookie, &attrs);
if (err) return (err);
if ((err = (*s)(stream->casio_stream_cookie, &attrs))) {
stream->casio_stream_lasterr = err;
return (err);
}
memcpy(&stream->casio_stream_attrs, &attrs,
sizeof(casio_streamattrs_t));
stream->casio_stream_lasterr = 0;
return (0);
}
@ -122,17 +151,22 @@ int CASIO_EXPORT casio_set_attrs(casio_stream_t *stream,
{
int err; casio_stream_setattrs_t *s;
/* check if the attributes aren't valid */
if (!attrs) return (casio_error_invalid);
/* Check if the attributes aren't valid. */
/* check if the callback exists */
if (!stream) return (casio_error_op);
s = getcb(stream, setattrs);
failure(!s, casio_error_op)
if (!attrs)
return (casio_error_invalid);
/* call it */
err = (*s)(stream->casio_stream_cookie, attrs);
failure(err, err)
/* Check if the callback exists. */
if (!stream
|| !(s = stream->casio_stream_callbacks.casio_streamfuncs_setattrs)) {
err = casio_error_op;
goto fail;
}
/* Call it. */
if ((err = (*s)(stream->casio_stream_cookie, attrs)))
goto fail;
memcpy(&stream->casio_stream_attrs, attrs, sizeof(casio_streamattrs_t));
err = 0;

View File

@ -0,0 +1,78 @@
/* ****************************************************************************
* stream/builtin/builtin.h -- stream builtins.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LOCAL_STREAM_BUILTIN_H
# define LOCAL_STREAM_BUILTIN_H 2018051601
# include "../../internals.h"
/* ---
* List serial devices.
* --- */
/* List serial devices on Linux. */
# ifndef LIBCASIO_DISABLED_LINUX_SERIAL
CASIO_EXTERN int CASIO_EXPORT casio_iter_linux_serial
OF((casio_iter_t **casio__iterp));
# endif
/* List serial devices on MacOS/OS X. */
# ifndef LIBCASIO_DISABLED_MAC_SERIAL
CASIO_EXTERN int CASIO_EXPORT casio_iter_mac_serial
OF((casio_iter_t **casio__iterp));
# endif
/* List serial devices on Microsoft Windows. */
# ifndef LIBCASIO_DISABLED_WINDOWS
CASIO_EXTERN int CASIO_EXPORT casio_iter_windows_serial
OF((casio_iter_t **casio__iterp));
# endif
/* ---
* Open a serial stream.
* --- */
/* Open a serial stream using the STREAMS interface. */
# ifndef LIBCASIO_DISABLED_STREAMS
CASIO_EXTERN int CASIO_EXPORT casio_open_streams_serial
OF((casio_stream_t **casio__streamp, char const *casio__path,
casio_streamattrs_t const *casio__attrs));
# endif
/* ---
* Open a USB stream.
* --- */
/* Open a USB stream using libusb. */
# ifndef LIBCASIO_DISABLED_LIBUSB
CASIO_EXTERN int CASIO_EXPORT casio_open_libusb_usb
OF((casio_stream_t **casio__streamp, int casio__bus, int casio__address));
# endif
/* Open a USB stream using the Windows API. */
# ifndef LIBCASIO_DISABLED_WINDOWS
CASIO_EXTERN int CASIO_EXPORT casio_open_windows_usb
OF((casio_stream_t **casio__streamp, int casio__bus, int casio__address));
# endif
#endif /* LOCAL_STREAM_BUILTIN_H */

View File

@ -16,7 +16,7 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#include "builtin.h"
/* ---
* Cookie structure.
@ -38,17 +38,18 @@ struct thecookie {
* @arg cookie the cookie.
* @arg data the data pointer.
* @arg size the data size.
* @arg timeout the timeout.
* @return the error code (0 if ok).
*/
CASIO_LOCAL int csum32_read(struct thecookie *cookie,
unsigned char *dest, size_t size)
unsigned char *dest, size_t size, unsigned int timeout)
{
int err;
/* Make the call. */
err = casio_read(cookie->_stream, dest, size);
err = casio_read(cookie->_stream, dest, size, timeout);
if (err) return (err);
/* Make the checksum. */
@ -72,9 +73,13 @@ CASIO_LOCAL int csum32_close(struct thecookie *cookie)
}
/* Callbacks. */
CASIO_LOCAL const casio_streamfuncs_t csum32_callbacks =
casio_stream_callbacks_for_virtual(csum32_close,
csum32_read, NULL, NULL);
CASIO_LOCAL casio_streamfuncs_t const csum32_callbacks = {
(casio_stream_close_t *)csum32_close,
(casio_stream_read_t *)csum32_read,
NULL, NULL,
NULL, NULL, NULL, NULL
};
/* ---
* Main functions.

View File

@ -1,6 +1,6 @@
/* ****************************************************************************
* stream/builtin/file.c -- built-in FILE stream.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
* Copyright (C) 2016-2018 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
@ -16,11 +16,12 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#include "builtin.h"
#ifndef LIBCASIO_DISABLED_FILE
# include <stdlib.h>
# include <string.h>
# include <errno.h>
# if defined(__linux__)
# include <stdio_ext.h>
# else
@ -46,14 +47,19 @@ typedef struct {
* @arg cookie the cookie.
* @arg data the data pointer
* @arg size the data size.
* @arg timeout the timeout.
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_file_read(file_cookie_t *cookie,
unsigned char *dest, size_t size)
unsigned char *dest, size_t size, unsigned int timeout)
{
size_t recv;
/* TODO: is there a way to set a timeout on this sort of read? */
(void)timeout;
/* Main receiving loop. */
recv = 0;
@ -124,14 +130,19 @@ CASIO_LOCAL int casio_file_read(file_cookie_t *cookie,
* @arg cookie the cookie.
* @arg data the source
* @arg size the source size
* @arg timeout the timeout.
* @return the error code (0 if ok)
*/
CASIO_LOCAL int casio_file_write(file_cookie_t *cookie,
const unsigned char *data, size_t size)
const unsigned char *data, size_t size, unsigned int timeout)
{
size_t sent;
/* TODO: is there a way to set a timeout on this sort of read? */
(void)timeout;
/* Main sending. */
sent = fwrite(data, size, 1, cookie->_wstream);
@ -221,9 +232,14 @@ CASIO_LOCAL int casio_file_close(file_cookie_t *cookie)
* Opening functions.
* --- */
CASIO_LOCAL const casio_streamfuncs_t casio_file_callbacks =
casio_stream_callbacks_for_virtual(casio_file_close, casio_file_read,
casio_file_write, casio_file_seek);
CASIO_LOCAL casio_streamfuncs_t const casio_file_callbacks = {
(casio_stream_close_t *)casio_file_close,
(casio_stream_read_t *)casio_file_read,
(casio_stream_write_t *)casio_file_write,
(casio_stream_seek_t *)casio_file_seek,
NULL, NULL, NULL, NULL
};
/**
* casio_open_stream_file:

View File

@ -17,7 +17,7 @@
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LOCAL_STREAM_BUILTIN_LIBUSB_H
# include "../../../internals.h"
# include "../builtin.h"
# ifndef LIBCASIO_DISABLED_LIBUSB
# include <libusb.h>

View File

@ -16,7 +16,7 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#include "builtin.h"
/* Cookie structure. */
@ -37,11 +37,12 @@ typedef struct {
* @arg vcookie the cookie (uncasted).
* @arg data the data pointer.
* @arg size the data size.
* @arg timeout the timeout (in ms).
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_limited_read(void *vcookie, unsigned char *dest,
size_t size)
size_t size, unsigned int timeout)
{
int err; limited_cookie_t *cookie = (void*)vcookie;
size_t left;
@ -60,7 +61,7 @@ CASIO_LOCAL int casio_limited_read(void *vcookie, unsigned char *dest,
return (casio_error_eof);
}
if ((err = casio_read(cookie->_stream, dest, size))) {
if ((err = casio_read(cookie->_stream, dest, size, timeout))) {
cookie->_left = 0; /* XXX: depends on the error? */
return (err);
}
@ -84,9 +85,12 @@ CASIO_LOCAL int casio_limited_close(void *vcookie)
/* Callbacks. */
CASIO_LOCAL const casio_streamfuncs_t casio_limited_callbacks =
casio_stream_callbacks_for_virtual(casio_limited_close,
casio_limited_read, NULL, NULL);
CASIO_LOCAL const casio_streamfuncs_t casio_limited_callbacks = {
(casio_stream_close_t *)casio_limited_close,
(casio_stream_read_t *)casio_limited_read,
NULL, NULL,
NULL, NULL, NULL, NULL
};
/* ---
* Main functions.

View File

@ -0,0 +1,163 @@
/* ****************************************************************************
* comlist/builtin/linux.c -- find out Linux serial devices.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../builtin.h"
#ifndef LIBCASIO_DISABLED_LINUX_SERIAL
# include <sys/stat.h>
# include <dirent.h>
# include <fcntl.h>
# include <unistd.h>
# include <errno.h>
typedef struct lincookie {
char *path;
char *devname;
size_t path_max;
DIR *dp;
char *start;
} lincookie_t;
/**
* next_serial_port:
* Get the next serial port.
*
* @arg cookie the lincookie.
* @arg ptr the pointer to the next path.
* @return the error code (0 if ok).
*/
CASIO_LOCAL int CASIO_EXPORT next_serial_port(lincookie_t *cookie,
char const **ptr)
{
struct dirent *dr;
struct stat st;
ssize_t rl;
char *res;
while (1) {
/* Get the next entry. */
if (!(dr = readdir(cookie->dp)))
return (casio_error_iter);
/* Copy that into the path and check the type. */
strcpy(cookie->start, dr->d_name);
if (lstat(cookie->path, &st) || (st.st_mode & S_IFMT) != S_IFLNK)
continue;
/* Get the destination path. */
rl = readlink(cookie->path, cookie->devname, PATH_MAX + 1);
if (rl < 0)
continue;
cookie->devname[rl] = 0;
/* If the path is a relative one, adapt it. */
if (cookie->devname[0] != '/') {
strcpy(cookie->start, cookie->devname);
if (!(res = realpath(cookie->path, cookie->devname)))
continue;
}
break;
}
*ptr = cookie->devname;
return (0);
}
/**
* end_iter:
* End the iterator by freeing all related allocated resources.
*
* @arg cookie the cookie.
*/
CASIO_LOCAL void CASIO_EXPORT end_iter(lincookie_t *cookie)
{
closedir(cookie->dp);
casio_free(cookie);
}
/* Functions. */
CASIO_LOCAL casio_iter_funcs_t linux_serial_functions = {
(casio_next_t *)&next_serial_port,
NULL,
(casio_end_t *)&end_iter
};
/**
* casio_iter_linux_serial:
* List serial ports under Linux.
*
* Links in the /dev/serial/by-id/ should resolve to relative paths, but
* I also managed absolute paths, in case.
*
* @arg iterp the iterator to create.
* @return the error.
*/
int CASIO_EXPORT casio_iter_linux_serial(casio_iter_t **iterp)
{
lincookie_t *cookie;
size_t path_max;
/* Get the maximum path size.
* Snippet found in `man 3 realpath`, glibc version. */
#ifdef PATH_MAX
path_max = PATH_MAX;
#else
path_max = pathconf(path, _PC_PATH_MAX);
if (path_max <= 0)
path_max = 4096;
#endif
++path_max;
/* Create the cookie. */
if (!(cookie = casio_alloc(sizeof(*cookie) + path_max + path_max, 1)))
return (casio_error_alloc);
cookie->path = (char *)(void *)&cookie[1];
cookie->devname = cookie->path + path_max;
/* Open the directory stream. */
strcpy(cookie->path, "/dev/serial/by-id/");
if (!(cookie->dp = opendir(cookie->path))) {
casio_free(cookie);
/* TODO: check errno */
return (casio_error_unknown);
}
/* Prepare what's left to prepare in the cookie. */
cookie->start = strchr(cookie->path, '\0');
cookie->path_max = path_max;
/* Create the iterator. */
return (casio_iter(iterp, cookie, linux_serial_functions));
}
# endif /* __linux__ */

View File

@ -0,0 +1,122 @@
/* ****************************************************************************
* comlist/builtin/macos.c -- find out MacOS/OS X serial devices.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../builtin.h"
#ifndef LIBCASIO_DISABLED_MAC_SERIAL
# include <dirent.h>
typedef struct {
char *path;
DIR *dp;
char *start;
} icookie_t;
/**
* next_serial_port:
* Get the next serial port.
*
* @arg cookie the iCookie.
* @arg ptr the pointer to the next path.
* @return the error code (0 if ok).
*/
CASIO_LOCAL int CASIO_EXPORT next_serial_port(icookie_t *cookie,
char const **ptr)
{
struct dirent *dr;
while (1) {
/* Get the next entry. */
if (!(dr = readdir(cookie->dp)))
return (casio_error_iter);
/* Check the name. */
if (strncmp(dr->d_name, "cu.", 3))
continue;
/* We have found a serial port!
* Just copy it into our buffer and return it. */
strcpy(cookie->start, dr->d_name);
break;
}
*ptr = cookie->path;
return (0);
}
/**
* end_iter:
* End the iterator by freeing all related allocated resources.
*
* @arg cookie the iCookie.
*/
CASIO_LOCAL void CASIO_EXPORT end_iter(icookie_t *cookie)
{
closedir(d);
casio_free(cookie);
}
/* Functions. */
CASIO_LOCAL casio_iter_funcs_t mac_serial_functions = {
(casio_next_t *)&next_serial_port,
NULL,
(casio_end_t *)&end_iter
};
/**
* casio_iter_mac_serial:
* Iterate on serial devices under MacOS/OS X.
*
* @arg iterp the iterator to create.
* @return the error.
*/
int CASIO_EXPORT casio_iter_mac_serial(casio_iter_t **iterp)
{
icookie_t *cookie;
/* Create the cookie. */
if (!(cookie = casio_alloc(1, sizeof(icookie_t) + PATH_MAX + 1)))
return (casio_error_alloc);
cookie->path = (char *)(void *)&cookie[1];
/* Prepare the path and open the directory stream. */
strcpy(cookie->path, "/dev/");
cookie->start = strchr(cookie->path, '\0');
if (!(cookie->dp = opendir(cookie->path))) {
casio_free(cookie);
/* TODO: check errno */
return (casio_error_unknown);
}
/* Create the iterator. */
return (casio_iter(iterp, cookie, mac_serial_functions));
}
#endif /* LIBCASIO_DISABLED_MAC_SERIAL */

View File

@ -16,9 +16,10 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#include "builtin.h"
/* Cookie structure. */
/* cookie structure */
typedef struct {
unsigned char *_memory;
casio_off_t _size, _offset;
@ -35,13 +36,20 @@ typedef struct {
* @arg vcookie the cookie (uncasted)
* @arg data the data pointer.
* @arg size the data size.
* @arg timeout the timeout (in ms).
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_memory_read(void *vcookie, unsigned char *dest, size_t size)
CASIO_LOCAL int casio_memory_read(void *vcookie, unsigned char *dest,
size_t size, unsigned int timeout)
{
memory_cookie_t *cookie = (void*)vcookie;
/* Timeouts while reading memory? Are you serious?
* Going quicker is impossible! */
(void)timeout;
if (((size_t)-1 - cookie->_offset) < size) /* overflow */
return (casio_error_read);
if (cookie->_offset + (casio_off_t)size > cookie->_size) {
@ -62,14 +70,20 @@ CASIO_LOCAL int casio_memory_read(void *vcookie, unsigned char *dest, size_t siz
* @arg vcookie the cookie (uncasted).
* @arg data the data pointer.
* @arg size the data size.
* @arg timeout the timeout (in ms).
* @return the error code (0 if ok).
*/
CASIO_LOCAL int casio_memory_write(void *vcookie, const unsigned char *data,
size_t size)
size_t size, unsigned int timeout)
{
memory_cookie_t *cookie = (void*)vcookie;
/* Timeouts while reading memory? Are you serious?
* Going quicker is impossible! */
(void)timeout;
if (((size_t)-1 - cookie->_offset) < size) /* overflow */
return (casio_error_write);
if (cookie->_offset + (casio_off_t)size > cookie->_size) {
@ -142,9 +156,14 @@ CASIO_LOCAL int casio_memory_close(void *vcookie)
}
/* Callbacks. */
CASIO_LOCAL const casio_streamfuncs_t casio_memory_callbacks =
casio_stream_callbacks_for_virtual(casio_memory_close,
casio_memory_read, casio_memory_write, casio_memory_seek);
CASIO_LOCAL casio_streamfuncs_t const casio_memory_callbacks = {
(casio_stream_close_t *)casio_memory_close,
(casio_stream_read_t *)casio_memory_read,
(casio_stream_write_t *)casio_memory_write,
(casio_stream_seek_t *)casio_memory_seek,
NULL, NULL, NULL, NULL
};
/* ---
* Opening functions.

View File

@ -18,7 +18,7 @@
* ************************************************************************* */
#ifndef LOCAL_STREAM_BUILTIN_STREAMS_H
# define LOCAL_STREAM_BUILTIN_STREAMS_H 1
# include "../../../internals.h"
# include "../builtin.h"
# ifndef LIBCASIO_DISABLED_STREAMS
# include <sys/stat.h>
# include <sys/ioctl.h>

View File

@ -0,0 +1,183 @@
/* ****************************************************************************
* comlist/builtin/windows.c -- find out serial devices on MS-Windows.
* Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../../internals.h"
#ifndef LIBCASIO_DISABLED_WINDOWS
/* These headers only work because I've redefined the version at the
* beginning of `internals.h`! */
# include <windows.h>
# include <setupapi.h>
# include <usbiodef.h>
# include <winerror.h>
/* The cookie structure. */
typedef struct {
HKEY hkey;
char *value;
char *data;
int erroneous;
DWORD i; /* index of the key to read */
DWORD value_size;
DWORD data_size;
} cookie_t, *PSP_COOKIE;
/**
* next_serial_port:
* Get the next serial port.
*
* @arg cookie the cookie.
* @arg ptr the pointer to the next path.
* @return the error code (0 if ok).
*/
CASIO_LOCAL int CASIO_EXPORT next_serial_port(cookie_t *cookie,
char const **ptr)
{
DWORD werr;
DWORD curval, datasize, type;
if (cookie->erroneous)
return (casio_error_unknown);
while (1) {
/* Get the next iteration from the original function. */
curval = cookie->value_size;
curdata = cookie->data_size;
switch ((werr = RegEnumValue(hkey, cookie->i++, value, &curval, NULL,
&type, (BYTE *)data, &curdata))) {
case 0:
/* Nothing wrong, check what's next. */
break;
case ERROR_NO_MORE_ITEMS:
/* We've arrived at the end of the original iterator. */
return (casio_error_iter);
case ERROR_MORE_DATA:
/* Our buffers weren't big enough. Tough luck!
* Let's go to the next entry and just ignore this one. */
continue;
default:
/* Any error could have happened, and put the original iterator
* in an erroneous state. So we're going to be in an erroneous
* state too. */
msg((ll_error, "Error %08lu occurred, switching to erroneous "
"state."));
cookie->erroneous = 1;
return (casio_error_unknown);
}
/* Check the type. */
if (type != REG_SZ) {
/* Not the kind of register we were expecting.
* Never mind, let's carry on. */
continue;
}
break;
}
/* The key is useless to us, we just read it because we're obliged to.
* What is interesting is the register entry data. */
*ptr = cookie->data;
return (0);
}
/**
* end_iter:
* End the iterator by freeing all related allocated resources.
*
* @arg cookie the cookie.
*/
CASIO_LOCAL void CASIO_EXPORT end_iter(cookie_t *cookie)
{
RegCloseKey(cookie->hkey);
casio_free(cookie);
}
/* Functions to use for the iterator. */
CASIO_LOCAL casio_iter_funcs_t windows_serial_functions = {
(casio_next_t *)&next_serial_port,
NULL,
(casio_end_t *)&end_iter
};
/**
* casio_iter_windows_serial:
* Iterate on serial devices under MS-Windows.
*
* What I'm doing here is based on the source from Python 3.x's winreg
* module source and the MSDN documentation.
*
* @arg iterp the iterator to create.
* @return the error code (0 if ok).
*/
# define SERIAL_COMM_HKEY "HARDWARE\\DEVICEMAP\\SERIALCOMM"
int CASIO_EXPORT casio_iter_windows_serial(casio_iter_t **iterp)
{
cookie_t *cookie;
DWORD werr, value_size, data_size;
/* Create the cookie.
* 1024 should be enough for most cases (until a driver comes and
* makes up a name which is longer). */
value_size = 1024;
data_size = 1024;
if (!(cookie = casio_alloc(1, sizeof(*cookie) + value_size + data_size)))
return (casio_error_alloc);
cookie->value = (char *)(void *)&cookie[1];
cookie->data = cookie->value + value_size;
cookie->value_size = value_size;
cookie->data_size = data_size;
cookie->erroneous = 0;
cookie->i = 0;
/* Opening the registry key. */
msg((ll_info, "Opening HKEY_LOCAL_MACHINE\\" SERIAL_COMM_HKEY));
if ((werr = RegOpenKey(HKEY_LOCAL_MACHINE, SERIAL_COMM_HKEY,
&cookie->hkey))) {
msg((ll_error, "Encountered error %08lu while opening registry.",
werr));
casio_free(cookie);
return (casio_error_unknown);
}
return (casio_iter(iterp, cookie, &windows_serial_functions));
}
#endif

View File

@ -18,7 +18,7 @@
* ************************************************************************* */
#ifndef LOCAL_STREAM_BUILTIN_WINDOWS_H
# define LOCAL_STREAM_BUILTIN_WINDOWS_H 1
# include "../../../internals.h"
# include "../builtin.h"
# ifndef LIBCASIO_DISABLED_WINDOWS
# include <windows.h>
# include <setupapi.h>

View File

@ -100,26 +100,16 @@ int CASIO_EXPORT casio_get_lasterr(casio_stream_t *stream)
int CASIO_EXPORT casio_get_attrs(casio_stream_t *stream,
casio_streamattrs_t *attrs)
{
if (!getcb(stream, setattrs)) return (casio_error_op);
casio_stream_setattrs_t *st;
/* Check that attributes have a meaning here. */
if (!(st = stream->casio_stream_callbacks.casio_streamfuncs_setattrs))
return (casio_error_op);
/* Return the attributes. */
memcpy(attrs, &stream->casio_stream_attrs,
sizeof(casio_streamattrs_t)); /* DANGEROUS: ABI COMPAT XXX */
return (0);
}
/**
* casio_get_timeouts:
* Get the timeouts of a libcasio stream.
*
* @arg stream the stream to get the timeouts of.
* @arg timeouts the timeouts to get.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_get_timeouts(casio_stream_t *stream,
casio_timeouts_t *timeouts)
{
if (!getcb(stream, settm)) return (casio_error_op);
memcpy(timeouts, &stream->casio_stream_timeouts,
sizeof(casio_timeouts_t)); /* DANGEROUS: ABI COMPAT XXX */
return (0);
}

60
lib/stream/list.c Normal file
View File

@ -0,0 +1,60 @@
/* ****************************************************************************
* stream/list.c -- find out serial devices.
* Copyright (C) 2016-2018 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "stream.h"
#if !defined(LIBCASIO_DISABLED_LINUX_SERIAL)
# define ISF &casio_iter_linux_serial
#elif !defined(LIBCASIO_DISABLED_WINDOWS)
# define ISF &casio_iter_windows_serial
#elif !defined(LIBCASIO_DISABLED_MAC_SERIAL)
# define ISF &casio_iter_mac_serial
#else
# define ISF NULL
#endif
CASIO_LOCAL casio_iter_serial_t *iter_serial_func = ISF;
/**
* casio_set_iter_serial_func:
* Set the function to iterate on serial devices.
*
* @arg func the function.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_set_iter_serial_func(casio_iter_serial_t *func)
{
iter_serial_func = func ? func : ISF;
return (0);
}
/**
* casio_iter_serial:
* Get available serial ports.
*
* @arg iterp the iterator to make.
* @return the error (if any).
*/
int CASIO_EXPORT casio_iter_serial(casio_iter_t **iterp)
{
if (!iter_serial_func)
return (casio_error_op);
return ((*iter_serial_func)(iterp));
}

View File

@ -50,28 +50,50 @@ int CASIO_EXPORT casio_open_stream(casio_stream_t **pstream,
stream->casio_stream_mode = 0;
c = &stream->casio_stream_callbacks;
memset(c, 0, sizeof(casio_streamfuncs_t));
c->casio_streamfuncs_close = callbacks->casio_streamfuncs_close;
c->casio_streamfuncs_settm = callbacks->casio_streamfuncs_settm;
if ((mode & CASIO_OPENMODE_READ) && callbacks->casio_streamfuncs_read) {
stream->casio_stream_mode |= CASIO_OPENMODE_READ;
c->casio_streamfuncs_read = callbacks->casio_streamfuncs_read;
}
c->casio_streamfuncs_read = callbacks->casio_streamfuncs_read;
} else
c->casio_streamfuncs_read = NULL;
if ((mode & CASIO_OPENMODE_WRITE) && callbacks->casio_streamfuncs_write) {
stream->casio_stream_mode |= CASIO_OPENMODE_WRITE;
c->casio_streamfuncs_write = callbacks->casio_streamfuncs_write;
}
} else
c->casio_streamfuncs_write = NULL;
if (mode & (CASIO_OPENMODE_READ | CASIO_OPENMODE_WRITE))
c->casio_streamfuncs_seek = callbacks->casio_streamfuncs_seek;
c->casio_streamfuncs_seek = callbacks->casio_streamfuncs_seek;
else
c->casio_streamfuncs_seek = NULL;
if ((mode & CASIO_OPENMODE_SERIAL)
&& callbacks->casio_streamfuncs_setattrs) {
stream->casio_stream_mode |= CASIO_OPENMODE_SERIAL;
c->casio_streamfuncs_setattrs = callbacks->casio_streamfuncs_setattrs;
}
} else
c->casio_streamfuncs_setattrs = NULL;
if ((mode & CASIO_OPENMODE_SCSI) && callbacks->casio_streamfuncs_scsi) {
stream->casio_stream_mode |= CASIO_OPENMODE_SCSI;
c->casio_streamfuncs_scsi = callbacks->casio_streamfuncs_scsi;
} else
c->casio_streamfuncs_scsi = NULL;
if ((mode & CASIO_OPENMODE_USB)
&& callbacks->casio_streamfuncs_usb_send_bulk
&& callbacks->casio_streamfuncs_usb_recv_bulk) {
stream->casio_stream_mode |= CASIO_OPENMODE_USB;
c->casio_streamfuncs_usb_send_bulk =
callbacks->casio_streamfuncs_usb_send_bulk;
c->casio_streamfuncs_usb_recv_bulk =
callbacks->casio_streamfuncs_usb_recv_bulk;
} else {
c->casio_streamfuncs_usb_send_bulk = NULL;
c->casio_streamfuncs_usb_recv_bulk = NULL;
}
/* Initialize the stream properties. */
@ -80,7 +102,6 @@ int CASIO_EXPORT casio_open_stream(casio_stream_t **pstream,
stream->casio_stream_offset = ioff;
stream->casio_stream_lasterr = 0;
casio_init_attrs(stream);
casio_init_timeouts(stream);
err = 0;
fail:
@ -101,11 +122,14 @@ fail:
int CASIO_EXPORT casio_close(casio_stream_t *stream)
{
casio_stream_close_t *c;
casio_stream_close_t *cl;
if (!stream) return (0);
c = getcb(stream, close);
if (c) (*c)(stream->casio_stream_cookie);
if (!stream)
return (0);
if ((cl = stream->casio_stream_callbacks.casio_streamfuncs_close))
(*cl)(stream->casio_stream_cookie);
casio_free(stream);
return (0);
}

View File

@ -1,84 +0,0 @@
/* ****************************************************************************
* stream/open/com.c -- open a COM stream.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../stream.h"
#define NUM 5
/* Correspondance type. */
struct corresp {
int _valid;
casio_opencomstream_t *_opencom;
};
/* List of streams. */
CASIO_LOCAL struct corresp opencoms[NUM + 1] = {
#if !defined(LIBCASIO_DISABLED_STREAMS)
{1, casio_opencom_streams},
#endif
#if !defined(LIBCASIO_DISABLED_WINDOWS)
{1, casio_opencom_windows},
#endif
{0, NULL}
};
/**
* casio_add_default_com_stream:
* Add a serial stream opener.
*
* @arg function the function pointer to add.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_add_default_com_stream(casio_opencomstream_t *function)
{
struct corresp *c; int num;
for (c = opencoms, num = NUM; c->_valid && num; c++, num--);
if (!num) return (casio_error_op);
c->_valid = 1;
c->_opencom = function;
return (0);
}
/**
* casio_open_com_stream:
* Open the serial stream.
*
* @arg stream the stream to make.
* @arg path the serial device path.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_open_com_stream(casio_stream_t **stream,
const char *path)
{
int err; struct corresp *c = opencoms;
if (!c->_valid)
return (casio_error_op);
for (; c->_valid; c++) {
err = (*c->_opencom)(stream, path);
if (!err) return (0);
if (err != casio_error_nocalc)
return (err);
}
return (casio_error_nocalc);
}

65
lib/stream/open_serial.c Normal file
View File

@ -0,0 +1,65 @@
/* ****************************************************************************
* stream/open_serial.c -- open a serial stream.
* Copyright (C) 2017-2018 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "stream.h"
#if !defined(LIBCASIO_DISABLED_STREAMS)
# define OSF &casio_open_streams_serial
#elif !defined(LIBCASIO_DISABLED_WINDOWS)
# define OSF &casio_open_windows_serial
#else
# define OSF NULL
#endif
CASIO_LOCAL casio_open_serial_stream_t *open_serial_stream_func = OSF;
/**
* casio_set_open_serial_stream_func:
* Set the serial streams opener.
*
* NULL resets the function to its default.
*
* @arg function the function pointer to set.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_set_open_serial_stream_func(
casio_open_serial_stream_t *func)
{
open_serial_stream_func = func ? func : OSF;
return (0);
}
/**
* casio_open_serial_stream:
* Open the serial stream.
*
* @arg streamp the stream to make.
* @arg path the serial device path.
* @arg attrs the serial attributes.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_open_serial_stream(casio_stream_t **streamp,
char const *path, casio_streamattrs_t const *attrs)
{
if (!open_serial_stream_func)
return (casio_error_op);
return ((*open_serial_stream_func)(streamp, path, attrs));
}

View File

@ -1,5 +1,5 @@
/* ****************************************************************************
* stream/open/usb.c -- open a USB stream.
* stream/open_usb.c -- open a USB stream.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
@ -16,44 +16,31 @@
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../stream.h"
#define NUM 5
#include "stream.h"
/* Correspondance type. */
struct corresp {
int _valid;
casio_openusbstream_t *_openusb;
};
/* List of streams. */
CASIO_LOCAL struct corresp openusbs[NUM + 1] = {
#if !defined(LIBCASIO_DISABLED_LIBUSB)
{1, casio_openusb_libusb},
# define OUF &casio_open_libusb_usb
#elif !defined(LIBCASIO_DISABLED_WINDOWS)
# define OUF &casio_open_windows_usb
#else
# define OUF NULL
#endif
#if !defined(LIBCASIO_DISABLED_WINDOWS)
{1, casio_openusb_windows},
#endif
{0, NULL}
};
CASIO_LOCAL casio_open_usb_stream_t *open_usb_stream_func = OUF;
/**
* casio_add_default_usb_stream:
* Add a USB stream opener.
* casio_set_open_usb_stream_func:
* Set the USB streams opener.
*
* @arg function the function pointer to add.
* NULL rests the function to its default.
*
* @arg function the function pointer to set.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_add_default_usb_stream(casio_openusbstream_t *function)
int CASIO_EXPORT casio_set_open_usb_stream_func(casio_open_usb_stream_t *func)
{
struct corresp *c; int num;
for (c = openusbs, num = NUM; c->_valid && num; c++, num--);
if (!num)
return (casio_error_op);
c->_valid = 1;
c->_openusb = function;
open_usb_stream_func = func ? func : OUF;
return (0);
}
@ -69,24 +56,13 @@ int CASIO_EXPORT casio_add_default_usb_stream(casio_openusbstream_t *function)
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_open_usb_stream(casio_stream_t **stream,
int CASIO_EXPORT casio_open_usb_stream(casio_stream_t **streamp,
int bus, int address)
{
int err; struct corresp *c = openusbs;
if (bus < -1 || bus > 255 || address < -1 || address > 255)
return (casio_error_op);
if (!c->_valid)
if (!open_usb_stream_func)
return (casio_error_op);
for (; c->_valid; c++) {
err = (*c->_openusb)(stream, bus, address);
if (!err)
return (0);
if (err != casio_error_nocalc)
return (err);
}
return (casio_error_nocalc);
return ((*open_usb_stream_func)(streamp, bus, address));
}

View File

@ -25,20 +25,29 @@
* @arg stream the stream to read from.
* @arg dest the destination buffer.
* @arg size the amount of bytes to read.
* @arg timeout the timeout for the entire read.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_read(casio_stream_t *stream, void *dest, size_t size)
int CASIO_EXPORT casio_read(casio_stream_t *stream, void *dest, size_t size,
unsigned int timeout)
{
int err;
casio_stream_read_t *rd;
/* check if we can read */
failure(~stream->casio_stream_mode & CASIO_OPENMODE_READ, casio_error_read)
/* Check if we can read. */
/* read */
if (!size) return (0);
err = (*getcb(stream, read))(stream->casio_stream_cookie, dest, size);
if (err) {
if (~stream->casio_stream_mode & CASIO_OPENMODE_READ
|| !(rd = stream->casio_stream_callbacks.casio_streamfuncs_read)) {
err = casio_error_read;
goto fail;
}
/* Read. */
if (!size)
return (0);
if ((err = (*rd)(stream->casio_stream_cookie, dest, size, timeout))) {
msg((ll_error, "Stream reading failure: %s", casio_strerror(err)));
goto fail;
}

View File

@ -33,12 +33,10 @@ int CASIO_EXPORT casio_scsi_request(casio_stream_t *stream,
int err;
casio_stream_scsi_t *s;
s = getcb(stream, scsi);
if (!s)
return (casio_error_op);
err = (*s)(stream->casio_stream_cookie, request);
failure(err, err)
if (!(s = stream->casio_stream_callbacks.casio_streamfuncs_scsi))
return (casio_error_scsi);
if ((err = (*s)(stream->casio_stream_cookie, request)))
goto fail;
err = 0;
fail:

View File

@ -31,10 +31,14 @@
int CASIO_EXPORT casio_seek(casio_stream_t *stream, casio_off_t offset,
casio_whence_t whence)
{
int err; casio_stream_seek_t *s;
int err;
casio_stream_seek_t *s;
failure(whence != CASIO_SEEK_SET && whence != CASIO_SEEK_CUR
&& whence != CASIO_SEEK_END, casio_error_op)
if (whence != CASIO_SEEK_SET && whence != CASIO_SEEK_CUR
&& whence != CASIO_SEEK_END) {
err = casio_error_op;
goto fail;
}
/* Check if the job isn't already done. */
@ -44,12 +48,11 @@ int CASIO_EXPORT casio_seek(casio_stream_t *stream, casio_off_t offset,
/* Try to seek using the dedicated function. */
s = getcb(stream, seek);
if (s) {
if ((s = stream->casio_stream_callbacks.casio_streamfuncs_seek)) {
/* The callback exists, let's use it! */
err = (*s)(stream->casio_stream_cookie, &offset, whence);
failure(err, err)
if ((err = (*s)(stream->casio_stream_cookie, &offset, whence)))
goto fail;
} else if (whence == CASIO_SEEK_CUR && offset > 0
&& stream->casio_stream_mode & CASIO_OPENMODE_READ) {
/* Fallback mehod for skipping bytes: read until N bytes have
@ -64,7 +67,7 @@ int CASIO_EXPORT casio_seek(casio_stream_t *stream, casio_off_t offset,
/* Read that much from the stream. */
if ((err = casio_read(stream, buf, rd)))
if ((err = casio_read(stream, buf, rd, 0)))
goto fail;
to_skip -= rd;

View File

@ -17,31 +17,28 @@
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#ifndef LOCAL_STREAM_H
# define LOCAL_STREAM_H 1
# define LOCAL_STREAM_H 2018051701
# include "../internals.h"
# define failure(CASIO__COND, CASIO__ERR) \
if (CASIO__COND) { err = CASIO__ERR; goto fail; }
/* Pretty much everything about this structure is discussed
* in `libcasio/stream.h`. */
struct casio_stream_s {
/* stream information */
/* Stream information. */
casio_openmode_t casio_stream_mode;
void *casio_stream_cookie;
int casio_stream_lasterr;
/* private properties (do not modify these!) */
/* Private properties (do not modify these!). */
casio_off_t casio_stream_offset;
casio_streamattrs_t casio_stream_attrs;
casio_timeouts_t casio_stream_timeouts;
/* callbacks */
/* Callbacks. */
casio_streamfuncs_t casio_stream_callbacks;
};
/* Get a callback. */
#define getcb(CASIO__S, CASIO__NAME) \
((CASIO__S)->casio_stream_callbacks.casio_streamfuncs_ ## CASIO__NAME)
# include "builtin/builtin.h"
#endif

View File

@ -1,67 +0,0 @@
/* ****************************************************************************
* stream/timeouts.c -- set the timeouts.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "stream.h"
/**
* casio_init_timeouts:
* Initialize the timeouts of a libcasio stream.
*
* @arg stream the stream to initialize the timeouts of.
* @arg timeouts the timeouts to set.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_init_timeouts(casio_stream_t *stream)
{
static const casio_timeouts_t timeouts = {0, 0, 0};
return (casio_set_timeouts(stream, &timeouts));
}
/**
* casio_set_timeouts:
* Set the timeouts of a libcasio stream.
*
* @arg stream the stream to set the timeouts of.
* @arg timeouts the timeouts to set.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_set_timeouts(casio_stream_t *stream,
const casio_timeouts_t *timeouts)
{
int err; casio_stream_settm_t *s;
/* check if the callback exists */
if (!stream) return (casio_error_op);
s = getcb(stream, settm);
failure(!s, casio_error_op)
/* call it */
err = (*s)(stream->casio_stream_cookie, timeouts);
failure(err, err)
/* copy timeouts */
memcpy(&stream->casio_stream_timeouts, timeouts,
sizeof(casio_timeouts_t)); /* ABI XXX */
err = 0;
fail:
stream->casio_stream_lasterr = err;
return (err);
}

View File

@ -25,27 +25,38 @@
* @arg stream the stream to write to.
* @arg data the data to write.
* @arg size the amount of bytes to write.
* @arg timeout timeout for the entire write (in ms).
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_write(casio_stream_t *stream,
const void *data, size_t size)
const void *data, size_t size, unsigned int timeout)
{
int err;
casio_stream_write_t *wr;
/* check if we can write */
failure(~stream->casio_stream_mode & CASIO_OPENMODE_WRITE,
casio_error_write)
/* write */
if (!size) return (0);
err = (*getcb(stream, write))(stream->casio_stream_cookie, data, size);
if (err) {
if (~stream->casio_stream_mode & CASIO_OPENMODE_WRITE
|| !(wr = stream->casio_stream_callbacks.casio_streamfuncs_write)) {
err = casio_error_write;
goto fail;
}
/* Check that the job isn't already done. */
if (!size)
return (0);
/* Write the goddamn thing. */
if ((err = (*wr)(stream->casio_stream_cookie, data, size, timeout))) {
msg((ll_error, "Stream writing failure: %s", casio_strerror(err)));
goto fail;
}
/* move the cursor and return */
/* Move the cursor and return. */
stream->casio_stream_offset += size;
err = 0;
fail:
@ -59,12 +70,14 @@ fail:
*
* @arg stream the stream to write to.
* @arg car the character to write.
* @arg timeout the timeout to write it.
* @return the error code (0 if ok).
*/
int CASIO_EXPORT casio_write_char(casio_stream_t *stream, int car)
int CASIO_EXPORT casio_write_char(casio_stream_t *stream, int car,
unsigned int timeout)
{
unsigned char ccar = car;
char ccar = (char)car;
return (casio_write(stream, &ccar, 1));
return (casio_write(stream, &ccar, 1, timeout));
}

View File

@ -60,13 +60,13 @@ CASIO_LOCAL void casio_unixsleep(unsigned long ms)
CASIO_LOCAL casio_sleep_t *casio_sleep_callback = default_callback;
/**
* casio_set_sleep:
* casio_set_sleep_func:
* Set the sleep function.
*
* @arg func the function to set.
*/
void CASIO_EXPORT casio_set_sleep(casio_sleep_t *func)
void CASIO_EXPORT casio_set_sleep_func(casio_sleep_t *func)
{
casio_sleep_callback = func;
}

115
lib/utils/timer.c Normal file
View File

@ -0,0 +1,115 @@
/* ****************************************************************************
* utils/timer.c -- timer internals.
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
*
* This file is part of libcasio.
* libcasio is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 3.0 of the License,
* or (at your option) any later version.
*
* libcasio is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with libcasio; if not, see <http://www.gnu.org/licenses/>.
* ************************************************************************* */
#include "../internals.h"
/* ---
* Default functions for UNIX.
* --- */
#if _POSIX_C_SOURCE >= 199309L
# include <time.h>
struct casio_timer_s {
clockid_t clk_id;
struct timespec initial;
};
CASIO_LOCAL int default_get_timer(casio_timer_t **timerp)
{
casio_timer_t *timer;
if (!(timer = casio_alloc(sizeof(*timer), 1)))
return (casio_error_alloc);
#ifdef __linux__
timer->clk_id = CLOCK_MONOTONIC_COARSE;
#else
timer->clk_id = CLOCK_MONOTONIC;
#endif
if (clock_gettime(timer->clk_id, &timer->initial) < 0) {
casio_free(timer);
return (casio_error_unknown);
}
*timerp = timer;
return (0);
}
CASIO_LOCAL void default_free_timer(casio_timer_t *timer)
{
casio_free(timer);
}
CASIO_LOCAL int default_get_spent_time(casio_timer_t *timer,
unsigned long *spent)
{
struct timespec ts;
if (clock_gettime(timer->clk_id, &ts) < 0)
return (casio_error_unknown);
*spent = (ts.tv_sec - timer->initial.tv_sec) * 1000
+ (ts.tv_nsec - timer->initial.tv_nsec) / 1000000;
return (0);
}
#else
# define NO_DEFAULTS 1
#endif
/* ---
* Public API functions.
* --- */
#if NO_DEFAULTS
CASIO_LOCAL casio_get_timer_t *gettimer = NULL;
CASIO_LOCAL casio_get_spent_time_t *getspenttime = NULL;
#else
CASIO_LOCAL casio_get_timer_t *gettimer = &default_get_timer;
CASIO_LOCAL casio_get_spent_time_t *getspenttime = &default_get_spent_time;
#endif
#if NO_DEFAULTS || NO_TIMERFREE
CASIO_LOCAL casio_free_timer_t *freetimer = NULL;
#else
CASIO_LOCAL casio_free_timer_t *freetimer = &default_free_timer;
#endif
int CASIO_EXPORT casio_get_timer(casio_timer_t **timerp)
{
if (!gettimer)
return (casio_error_op);
return ((*gettimer)(timerp));
}
void CASIO_EXPORT casio_free_timer(casio_timer_t *timer)
{
if (!freetimer)
return ;
(*freetimer)(timer);
}
int CASIO_EXPORT casio_get_spent_time(casio_timer_t *timer,
unsigned long *spent)
{
if (!getspenttime)
return (casio_error_op);
return ((*getspenttime)(timer, spent));
}