From a774fa21ea8131e472378979b7f8d699ada176b5 Mon Sep 17 00:00:00 2001 From: "Thomas \"Cakeisalie5\" Touhey" Date: Wed, 21 Jun 2017 02:57:08 +0200 Subject: [PATCH] Added Protocol 7.00 MCS (unfinished), corrected Protocol 7.00 data streams, corrected MCS head correction/conversion, regrouped mem. alloc. --- Makefile | 48 ++--- Makefile.msg | 30 +-- Makefile.vars | 54 ++--- configure | 55 ++--- include/libcasio.h | 1 + include/libcasio/builtin.h | 10 +- include/libcasio/cdefs/endian.h | 8 +- include/libcasio/error.h | 1 + include/libcasio/format/cas.h | 2 +- include/libcasio/link.h | 6 + include/libcasio/mcs.h | 12 +- include/libcasio/mcsfile.h | 12 +- include/libcasio/mutex.h | 36 ++++ include/libcasio/protocol/seven.h | 5 +- include/libcasio/protocol/seven/commands.h | 25 ++- src/comlist/builtin/windows.c | 5 +- src/errors.c | 3 +- src/file/decode/casemul.c | 16 +- src/file/decode/std.c | 3 +- src/file/decode/std/eact.c.draft | 10 +- src/file/decode/std/fkey.c | 10 +- src/file/decode/std/lang.c | 12 +- src/file/decode/std/mcs.c | 1 + src/file/decode/std/picture.c | 10 +- src/file/file.h | 2 +- src/file/manage.c | 29 +-- src/link/open.c | 4 +- src/link/seven/command.c | 27 +++ src/link/seven/dataflow.c | 4 +- src/link/seven/datastream.c | 190 +++++++++++++++--- src/link/seven/send.c | 6 +- src/link/seven_mcs/delete.c | 50 +++++ src/link/seven_mcs/get.c | 123 ++++++++++++ src/link/seven_mcs/list.c | 95 +++++++++ src/link/seven_mcs/open.c | 73 +++++++ src/link/seven_mcs/put.c.draft | 61 ++++++ src/link/seven_mcs/seven_mcs.h | 41 ++++ src/link/usage/backup_rom.c | 2 +- src/link/usage/getscreen.c | 6 +- src/link/usage/server/seven.c | 7 +- src/log/manage.c | 1 + src/mcs/local/find.c | 4 +- src/mcs/local/list.c | 5 +- src/mcs/local/local.h | 6 +- src/mcs/local/open.c | 16 +- src/mcs/open.c | 4 +- src/mcsfile/decode/cas.c | 33 ++- src/mcsfile/decode/cas/screenshot.c | 5 +- src/mcsfile/decode/mcs.c | 33 ++- src/mcsfile/decode/mcs/picture.c | 12 +- src/mcsfile/decode/mcs/spreadsheet.c | 4 +- src/mcsfile/decode/mcs/string.c | 4 +- src/mcsfile/duplicate.c | 4 +- src/mcsfile/free.c | 18 +- src/mcsfile/head.c | 85 ++++++++ src/mcsfile/make.c | 4 +- src/mcsfile/mcsfile.h | 18 +- src/mcsfile/prepare.c | 26 +-- src/mcsfile/{corresp => reference}/cas_app.c | 20 +- src/mcsfile/{corresp => reference}/cas_data.c | 22 +- src/mcsfile/{corresp => reference}/mcs.c | 62 ++---- src/mcsfile/reference/reference.h | 42 ++++ src/stream/builtin/file.c | 4 +- src/stream/builtin/libusb.c | 6 +- src/stream/builtin/limited.c | 4 +- src/stream/builtin/memory.c | 4 +- src/stream/builtin/streams.c | 4 +- src/stream/builtin/windows.c | 24 +-- src/stream/open.c | 6 +- src/stream/read.c | 5 +- src/stream/write.c | 7 +- src/utils/alloc.c | 45 +++++ src/utils/mutex.c | 80 ++++++++ 73 files changed, 1314 insertions(+), 398 deletions(-) create mode 100644 include/libcasio/mutex.h create mode 100644 src/link/seven_mcs/delete.c create mode 100644 src/link/seven_mcs/get.c create mode 100644 src/link/seven_mcs/list.c create mode 100644 src/link/seven_mcs/open.c create mode 100644 src/link/seven_mcs/put.c.draft create mode 100644 src/link/seven_mcs/seven_mcs.h create mode 100644 src/mcsfile/head.c rename src/mcsfile/{corresp => reference}/cas_app.c (87%) rename src/mcsfile/{corresp => reference}/cas_data.c (92%) rename src/mcsfile/{corresp => reference}/mcs.c (91%) create mode 100644 src/mcsfile/reference/reference.h create mode 100644 src/utils/alloc.c create mode 100644 src/utils/mutex.c diff --git a/Makefile b/Makefile index 80796da..b9a8ba5 100755 --- a/Makefile +++ b/Makefile @@ -1,12 +1,12 @@ #!/usr/bin/make -f -#******************************************************************************# -# Include variables and message subsystem # -#******************************************************************************# +#*****************************************************************************# +# Include variables and message subsystem # +#*****************************************************************************# include Makefile.vars Makefile.msg -#******************************************************************************# -# General targets # -#******************************************************************************# +#*****************************************************************************# +# General targets # +#*****************************************************************************# # Build everything. all: all-lib $(if $(INSTALL_MANPAGES),all-doc) @@ -52,9 +52,9 @@ dist: mrproper .PHONY: all mostlyclean mclean clean fclean mrproper re .PHONY: dist install uninstall reinstall -#******************************************************************************# -# Configuration (version) checking dependencies # -#******************************************************************************# +#*****************************************************************************# +# Configuration (version) checking dependencies # +#*****************************************************************************# # Define the dependencies. CHECKCFG := $(if $(shell test -f Makefile.cfg || echo y),check-config, \ $(if $(shell [ "$(VERSION)" = "$(CONFIG_VERSION)" ] || echo y), \ @@ -71,9 +71,9 @@ dist: mrproper @false .PHONY: check-config check-config-version -#******************************************************************************# -# Information getting from the Makefile variables # -#******************************************************************************# +#*****************************************************************************# +# Information getting from the Makefile variables # +#*****************************************************************************# # Get the project name. getname: @echo lib$(NAME) @@ -87,9 +87,9 @@ dist: mrproper @echo "$(MAINTAINER_NAME) <$(MAINTAINER_MAIL)>" .PHONY: getname getauthor getmail getversion -#******************************************************************************# -# Library-specific targets # -#******************************************************************************# +#*****************************************************************************# +# Library-specific targets # +#*****************************************************************************# # Make the library. all-lib: $(CHECKCFG) $(if $(STATIC),$(ANAME),$(SONAME)) @@ -128,7 +128,8 @@ $(eval $(call make-obj-rule,$(src)))) re-lib: clean-lib all-lib # Install the library and development files. - LINK_TO_MAJOR := $(if $(INSTALL_DEVEL),$(if $(STATIC),,$(if $(FOR_WINDOWS),,y))) + LINK_TO_MAJOR := $(if $(INSTALL_DEVEL),$(if $(STATIC),,\ + $(if $(FOR_WINDOWS),,y))) IWINDLL := $(if $(FOR_WINDOWS),$(if $(STATIC),,y)) install-lib: all-lib $(if $(INSTALL_DEVEL),install-cfgtool) $(call imsg,Installing the library.) @@ -171,9 +172,9 @@ $(eval $(call make-obj-rule,$(src)))) .PHONY: all-lib mostlyclean-lib mclean-lib clean-lib re-lib .PHONY: install-lib uninstall-lib reinstall-lib -#******************************************************************************# -# Configuration tools-related # -#******************************************************************************# +#*****************************************************************************# +# Configuration tools-related # +#*****************************************************************************# # Install it. install-cfgtool: $(CHECKCFG) $(call imsg,Installing the configuration tool.) @@ -185,7 +186,8 @@ $(eval $(call make-obj-rule,$(src)))) && chmod 755 "$(IBINDIR)/lib$(NAME)-config") $(if $(TARGET),$(call qcmd,$(INST) -m 755 -d "$(HBINDIR)")) $(if $(TARGET),$(call qcmd,$(LN) -r \ - "$(IBINDIR)/lib$(NAME)-config" "$(HBINDIR)/$(TARGET)lib$(NAME)-config")) + "$(IBINDIR)/lib$(NAME)-config" \ + "$(HBINDIR)/$(TARGET)lib$(NAME)-config")) $(call imsg,Installing the pkg-config configuration.) $(call qcmd,$(INST) -m 755 -d "$(IPKGDIR)") @@ -205,9 +207,9 @@ $(eval $(call make-obj-rule,$(src)))) $(if $(TARGET),"$(HBINDIR)/$(TARGET)lib$(NAME)-config")) .PHONY: install-cfgtool uninstall-cfgtool -#******************************************************************************# -# Documentation-related # -#******************************************************************************# +#*****************************************************************************# +# Documentation-related # +#*****************************************************************************# # Make all manpages. all-doc: $(foreach s,$(MAN_SECTIONS), $(MAN_$(s):%=$(MANDIR)/man$(s)/%.$(s))) diff --git a/Makefile.msg b/Makefile.msg index 186d90a..e44f4f2 100755 --- a/Makefile.msg +++ b/Makefile.msg @@ -1,9 +1,9 @@ #!/usr/bin/make -f # The Makefile message subsystem. # For nice logs. 5 dollars per log only. -#******************************************************************************# -# Colors and misc # -#******************************************************************************# +#*****************************************************************************# +# Colors and misc # +#*****************************************************************************# # Used colors ANSI modifiers escape codes color_green := 32 color_red := 31 @@ -15,12 +15,13 @@ define \n endef -#******************************************************************************# -# General messages # -#******************************************************************************# +#*****************************************************************************# +# General messages # +#*****************************************************************************# # Command message - display basic info about the command, and run it. define cmd -@$(if $(MAKE_FULL_LOG),,printf "\033[1;""$4""m>\033[0m \033[1m%s\033[0m %s\n" "$1" "$2";) +@$(if $(MAKE_FULL_LOG),,\ +printf "\033[1;""$4""m>\033[0m \033[1m%s\033[0m %s\n" "$1" "$2";) $(if $(MAKE_FULL_LOG),,@)$3 endef @@ -31,20 +32,21 @@ endef # Normal message - display it. define msg -$(if $(MAKE_FULL_LOG),,@printf "\033[1;""$2""m>\033[0m \033[1m%s\033[0m\n" "$1") +$(if $(MAKE_FULL_LOG),,\ +@printf "\033[1;""$2""m>\033[0m \033[1m%s\033[0m\n" "$1") endef -#******************************************************************************# -# Commands # -#******************************************************************************# +#*****************************************************************************# +# Commands # +#*****************************************************************************# # Build command define bcmd $(call cmd,$1,$2,$3,$(color_green)) endef -#******************************************************************************# -# Messages # -#******************************************************************************# +#*****************************************************************************# +# Messages # +#*****************************************************************************# # Remove message define rmsg $(call msg,$1,$(color_red)) diff --git a/Makefile.vars b/Makefile.vars index 7dbc3ef..e0716ab 100755 --- a/Makefile.vars +++ b/Makefile.vars @@ -1,15 +1,15 @@ #!/usr/bin/make -f -#******************************************************************************# -# Include configuration # -#******************************************************************************# +#*****************************************************************************# +# Include configuration # +#*****************************************************************************# # Do it -include Makefile.cfg # Correct target TARGET := $(if $(TARGET),$(TARGET)-) -#******************************************************************************# -# Project main information # -#******************************************************************************# +#*****************************************************************************# +# Project main information # +#*****************************************************************************# # Project name and description NAME := casio DESCRIPTION := Library for manipulating CASIO protocols and file formats. @@ -25,9 +25,9 @@ # Project version string VERSION := $(MAJOR).$(MINOR)$(if $(INDEV),-indev) -#******************************************************************************# -# Project directories # -#******************************************************************************# +#*****************************************************************************# +# Project directories # +#*****************************************************************************# # Headers directory - where all the headers are. INCDIR := ./include @@ -42,9 +42,9 @@ # Manpages directory - where the manpages will be put. MANDIR := ./man -#******************************************************************************# -# Object names # -#******************************************************************************# +#*****************************************************************************# +# Object names # +#*****************************************************************************# # Dynamic library name SONAME := $(if $(FOR_WINDOWS),lib$(NAME).dll,lib$(NAME).so.$(MAJOR)) SONAMES := $(if $(FOR_WINDOWS),lib$(NAME).dll,lib$(NAME).so.*) @@ -57,9 +57,9 @@ DEPS := libfontcharacter DEPS_PRIV := zlib $(if $(NO_LIBUSB),,libusb-1.0) ALLDEPS := $(DEPS) $(DEPS_PRIV) -#******************************************************************************# -# Binary utilities # -#******************************************************************************# +#*****************************************************************************# +# Binary utilities # +#*****************************************************************************# # Package configuration PKGCONFIG := $(TARGET)pkg-config @@ -67,7 +67,7 @@ CC := $(TARGET)gcc # - Check flags (warnings) CWERROR := all extra no-attributes no-unused-macros no-vla no-multichar -ifdef MORE_WARNINGS +ifneq ($(MORE_WARNINGS),) CWERROR += shadow write-strings redundant-decls format format-nonliteral \ format-security implicit-function-declaration \ date-time missing-prototypes return-type pointer-arith \ @@ -117,9 +117,9 @@ endif INST := install # GZipper GZIP := gzip -f -#******************************************************************************# -# Look up the sources and includes # -#******************************************************************************# +#*****************************************************************************# +# Look up the sources and includes # +#*****************************************************************************# # Look up the sources SRC := $(basename $(shell find $(SRCDIR) -mindepth 1 -type f \ -name "*.c" -printf "%P\n")) @@ -131,9 +131,9 @@ endif # Look up the includes INC := $(shell find $(INCDIR) -name "*.h") -#******************************************************************************# -# Look for manpages # -#******************************************************************************# +#*****************************************************************************# +# Look for manpages # +#*****************************************************************************# # Get the manpages sections and contents MAN_SECTIONS := define check-man @@ -141,14 +141,14 @@ define check-man MAN_$1 += $2 endef $(foreach doc, $(basename $(shell find $(DOCDIR) \ - -maxdepth 1 -mindepth 1 -printf "%P\n" -type f -or -type l -name "*.*.txt")), \ + -maxdepth 1 -mindepth 1 -printf "%P\n" -type f -or -type l -name "*.*.txt")),\ $(eval $(call check-man,$(patsubst .%,%,$(suffix $(doc))),$(basename $(doc))))) # Remove duplicate sections. MAN_SECTIONS := $(sort $(MAN_SECTIONS)) -#******************************************************************************# -# Check for DESTDIR (add as prefix to installation root) # -#******************************************************************************# +#*****************************************************************************# +# Check for DESTDIR (add as prefix to installation root) # +#*****************************************************************************# # Save original library and include dir. OIINCDIR := $(IINCDIR) OILIBDIR := $(ILIBDIR) @@ -161,4 +161,4 @@ $(if $(DESTDIR), $(foreach idir,\ IBINDIR IPKGDIR ILIBDIR IINCDIR IMANDIR HBINDIR, \ $(eval $(call add-dest-dir,$(idir))))) -# END OF FILE +# End of file. diff --git a/configure b/configure index 485f863..396400c 100755 --- a/configure +++ b/configure @@ -1,8 +1,8 @@ #!/bin/sh cd "$(dirname $0)" -#******************************************************************************# -# Defaults # -#******************************************************************************# +#*****************************************************************************# +# Defaults # +#*****************************************************************************# # Project variables [ -f Makefile.cfg ] && mv Makefile.cfg Makefile.cfg.tmp name="$(make -s getname)" @@ -46,9 +46,9 @@ install_devel=yes # Tweaks cflags= ldflags= -#******************************************************************************# -# Help message # -#******************************************************************************# +#*****************************************************************************# +# Help message # +#*****************************************************************************# usage() { cat <&2 </dev/null 2>/dev/null @@ -231,9 +232,9 @@ tools/write-header-config --version=${version} \ exec 3>&1 1>Makefile.cfg cat < # if BYTE_ORDER == LITTLE_ENDIAN -# define casio_int_be16toh(x) ntohs(CASIO__X) -# define casio_int_le16toh(x) (CASIO__X) -# define casio_int_be32toh(x) ntohl(CASIO__X) -# define casio_int_le32toh(x) (CASIO__X) +# define casio_int_be16toh(CASIO__X) ntohs(CASIO__X) +# define casio_int_le16toh(CASIO__X) (CASIO__X) +# define casio_int_be32toh(CASIO__X) ntohl(CASIO__X) +# define casio_int_le32toh(CASIO__X) (CASIO__X) # define casio_int_htobe16(CASIO__X) htons(CASIO__X) # define casio_int_htole16(CASIO__X) (CASIO__X) diff --git a/include/libcasio/error.h b/include/libcasio/error.h index 695def4..90f363a 100644 --- a/include/libcasio/error.h +++ b/include/libcasio/error.h @@ -40,6 +40,7 @@ typedef int casio_error_t; # define casio_error_op 0x03 /* an operation is not supported. */ # define casio_error_arg 0x04 /* an argument was invalid. */ # define casio_error_invalid 0x04 /* (alias) */ +# define casio_error_lock 0x05 /* mutex is locked */ /* Stream errors. */ diff --git a/include/libcasio/format/cas.h b/include/libcasio/format/cas.h index cd16c34..f4574ae 100644 --- a/include/libcasio/format/cas.h +++ b/include/libcasio/format/cas.h @@ -75,7 +75,7 @@ typedef struct casio_cas40_s { /* ************************************************************************* */ /* CASDYN header */ /* ************************************************************************* */ -/* The CASDYN (dynamic size) header appeared later. +/* The CASDYN (dynamic size, super header) header appeared later. * It is known in CaS as the protocol the CFX-9850G uses. * * This header format was previously named 'caspro' in libcasio, then CAS50 diff --git a/include/libcasio/link.h b/include/libcasio/link.h index 0c748ba..8404fe1 100644 --- a/include/libcasio/link.h +++ b/include/libcasio/link.h @@ -20,6 +20,7 @@ # define LIBCASIO_LINK_H # include "cdefs.h" # include "stream.h" +# include "mcs.h" # include "fs.h" # include "version.h" # include "picture.h" @@ -184,6 +185,11 @@ CASIO_EXTERN int CASIO_EXPORT casio_upload_and_run_file casio_link_progress_t *casio__disp, void *casio__pcookie)); # endif +/* Make the MCS interface (don't use it unless you know what you're doing). */ + +CASIO_EXTERN int CASIO_EXPORT casio_open_seven_mcs + OF((casio_mcs_t **casio__mcs, casio_link_t *casio__link)); + CASIO_END_DECLS CASIO_END_NAMESPACE # include "protocol/legacy.h" diff --git a/include/libcasio/mcs.h b/include/libcasio/mcs.h index 0c48aa0..b665617 100644 --- a/include/libcasio/mcs.h +++ b/include/libcasio/mcs.h @@ -41,24 +41,24 @@ typedef struct casio_mcsfuncs_s casio_mcsfuncs_t; * * Here are the callbacks you should set: */ -typedef int casio_mcs_get_t +typedef int casio_mcs_get_t OF((void *casio__cookie, casio_mcsfile_t **casio__mcsfile, casio_mcshead_t *casio__mcshead)); -typedef int casio_mcs_put_t +typedef int casio_mcs_put_t OF((void *casio__cookie, casio_mcsfile_t *casio__mcsfile)); -typedef int casio_mcs_delete_t +typedef int casio_mcs_delete_t OF((void *casio__cookie, casio_mcshead_t *casio__mcshead)); -typedef int casio_mcslist_t +typedef void casio_mcslist_t OF((void *casio__cookie, const casio_mcshead_t *casio__mcshead)); -typedef int casio_mcs_list_t +typedef int casio_mcs_list_t OF((void *casio__cookie, casio_mcslist_t *casio__mcslist, void *casio__mcslist_cookie)); -typedef int casio_mcs_close_t +typedef int casio_mcs_close_t OF((void *casio__cookie)); struct casio_mcsfuncs_s { diff --git a/include/libcasio/mcsfile.h b/include/libcasio/mcsfile.h index 82f4e8f..6745f43 100644 --- a/include/libcasio/mcsfile.h +++ b/include/libcasio/mcsfile.h @@ -271,6 +271,7 @@ typedef struct casio_mcshead_s { /* raw data */ unsigned int casio_mcshead_rawtype; + unsigned int casio_mcshead_cas_ext; casio_pictureformat_t casio_mcshead_picformat; /* strings */ @@ -278,7 +279,7 @@ typedef struct casio_mcshead_s { char casio_mcshead_password[9]; char casio_mcshead_group[17]; char casio_mcshead_dirname[9]; - char casio_mcshead_appname[4]; + char casio_mcshead_cas_app[4]; char casio_mcshead_datatype[3]; } casio_mcshead_t; /* ************************************************************************* */ @@ -318,9 +319,6 @@ typedef struct casio_mcsfile_s { CASIO_BEGIN_DECLS /* Make a main memory file, prepare it, and free it. */ -/* Manage a main memory file from a head, duplicate an existing main memory - * file, and free a main memory file. */ - CASIO_EXTERN int CASIO_EXPORT casio_make_mcsfile OF((casio_mcsfile_t **casio__handle, const casio_mcshead_t *casio__head)); CASIO_EXTERN int CASIO_EXPORT casio_prepare_mcsfile @@ -370,10 +368,8 @@ CASIO_EXTERN int CASIO_EXPORT casio_encode_casfile_part /* Correct a head (add raw data). */ -CASIO_EXTERN int CASIO_EXPORT casio_correct_mcsfile_head - OF((casio_mcshead_t *casio__head)); -CASIO_EXTERN int CASIO_EXPORT casio_correct_casfile_head - OF((casio_mcshead_t *casio__head)); +CASIO_EXTERN int CASIO_EXPORT casio_correct_mcshead + OF((casio_mcshead_t *casio__head, unsigned long casio__mcsfor)); /* Compare MCS files (for ordering). */ diff --git a/include/libcasio/mutex.h b/include/libcasio/mutex.h new file mode 100644 index 0000000..84fd64b --- /dev/null +++ b/include/libcasio/mutex.h @@ -0,0 +1,36 @@ +/* **************************************************************************** + * libcasio/mutex.h -- libcasio mutexes. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#ifndef LIBCASIO_MUTEX_H +# define LIBCASIO_MUTEX_H 1 +# include + +typedef int casio_mutex_t; + +CASIO_EXTERN void CASIO_EXPORT casio_init_mutex + OF((casio_mutex_t *casio__mutex)); + +CASIO_EXTERN int CASIO_EXPORT casio_lock_mutex + OF((casio_mutex_t *casio__mutex)); +CASIO_EXTERN int CASIO_EXPORT casio_trylock_mutex + OF((casio_mutex_t *casio__mutex)); + +CASIO_EXTERN void CASIO_EXPORT casio_unlock_mutex + OF((casio_mutex_t *casio__mutex)); + +#endif /* LIBCASIO_MUTEX_H */ diff --git a/include/libcasio/protocol/seven.h b/include/libcasio/protocol/seven.h index 19a38f1..ea8976e 100644 --- a/include/libcasio/protocol/seven.h +++ b/include/libcasio/protocol/seven.h @@ -256,11 +256,10 @@ CASIO_EXTERN int CASIO_EXPORT casio_seven_send_eack * so if you're using a classical command, you should use them instead. */ CASIO_EXTERN int CASIO_EXPORT casio_seven_send_cmd - OF((casio_link_t *casio__handle, - unsigned int casio__subtype)); + OF((casio_link_t *casio__handle, unsigned int casio__code)); CASIO_EXTERN int CASIO_EXPORT casio_seven_send_cmd_data OF((casio_link_t *casio__handle, - unsigned int casio__subtype, int casio__overwrite, + unsigned int casio__code, int casio__overwrite, unsigned int casio__datatype, unsigned long casio__filesize, const char *casio__arg0, const char *casio__arg1, const char *casio__arg2, const char *casio__arg3, diff --git a/include/libcasio/protocol/seven/commands.h b/include/libcasio/protocol/seven/commands.h index dae5ff5..d716338 100644 --- a/include/libcasio/protocol/seven/commands.h +++ b/include/libcasio/protocol/seven/commands.h @@ -27,17 +27,7 @@ CASIO_BEGIN_DECLS CASIO_EXTERN int CASIO_EXPORT casio_seven_send_typical_mcs_command OF((casio_link_t *casio__handle, int casio__code, casio_mcshead_t *casio__head, - casio_mcsfile_t *casio__file, - int casio__ow)); -/* - size_t sz = casio__file ? get_the_file_size(casio__file) : 0; - return (casio_seven_send_cmd_data(casio__handle, casio__code, casio__ow, - casio__head->casio_mcshead_rawtype, sz, - casio__head->casio_mcshead_dirname, - casio__head->casio_mcshead_name, - casio__head->casio_mcshead_group, - NULL, NULL, NULL)); -*/ + casio_mcsfile_t *casio__mcsfile, int casio__ow)); /* ************************************************************************* */ /* Basic commands */ /* ************************************************************************* */ @@ -100,19 +90,28 @@ CASIO_EXTERN int CASIO_EXPORT casio_seven_send_cmdsys_setlink # define casio_seven_cmdmcs_reqfile 0x24 # define casio_seven_send_cmdmcs_reqfile(CASIO__HANDLE, CASIO__HEAD) \ casio_seven_send_typical_mcs_command(CASIO__HANDLE, 0x24, \ - CASIO__HEAD, NULL, 0) + CASIO__HEAD, 0, 0) /* Send a file */ # define casio_seven_cmdmcs_sendfile 0x25 # define casio_seven_send_cmdmcs_sendfile(CASIO__HANDLE, CASIO__OW, \ CASIO__FILE) \ casio_seven_send_typical_mcs_command(CASIO__HANDLE, 0x25, \ - (CASIO__FILE)->casio_mcsfile_head, CASIO__FILE, CASIO__OW) + (CASIO__FILE)->casio_mcsfile_head, CASIO__OW) + +/* Delete a file */ +# define casio_seven_cmdmcs_delfile 0x26 +# define casio_seven_send_cmdmcs_delfile(CASIO__HANDLE, CASIO__HEAD) \ + casio_seven_send_typical_mcs_command(CASIO__HANDLE, 0x26, \ + (CASIO__HEAD), NULL, 0) /* Request all file information */ # define casio_seven_cmdmcs_reqallinfo 0x2D # define casio_seven_send_cmdmcs_reqallinfo(CASIO__HANDLE) \ casio_seven_send_cmd(CASIO__HANDLE, 0x2D) + +/* Send one file's information */ +# define casio_seven_cmdmcs_fileinfo 0x2E /* ************************************************************************* */ /* Storage commands */ /* ************************************************************************* */ diff --git a/src/comlist/builtin/windows.c b/src/comlist/builtin/windows.c index fd4f36a..081045c 100644 --- a/src/comlist/builtin/windows.c +++ b/src/comlist/builtin/windows.c @@ -54,7 +54,8 @@ int CASIO_EXPORT casio_comlist_windows(casio_list_com_t callback, void *cookie) /* prepare */ msg((ll_info, "Allocating enough space")); valsize = 1024; datasize = 1024; /* I DON'T CARE IT WORKS LALALA */ - if (!(value = malloc(valsize)) || !(data = malloc(datasize))) + if (!(value = casio_alloc(valsize, 1)) + || !(data = casio_alloc(datasize, 1))) goto fail; /* enumerate values */ @@ -81,7 +82,7 @@ int CASIO_EXPORT casio_comlist_windows(casio_list_com_t callback, void *cookie) fail: ifmsg(werr, (ll_error, "Got error %08lu", werr)); /* free, close the key and return ! */ - free(value); free(data); + casio_free(value); casio_free(data); if (hkey_open) RegCloseKey(hkey); return (werr ? casio_error_unknown : 0); } diff --git a/src/errors.c b/src/errors.c index 529877c..ab4d5c9 100644 --- a/src/errors.c +++ b/src/errors.c @@ -65,7 +65,8 @@ const char* CASIO_EXPORT casio_error_strings[128] = { NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, - /* Decoding errors. */ +/* Decoding errors. */ + "corrupted or unknown file format", "invalid checksum", "was recognized but not one of the allowed file types." diff --git a/src/file/decode/casemul.c b/src/file/decode/casemul.c index 00820a6..87fc07d 100644 --- a/src/file/decode/casemul.c +++ b/src/file/decode/casemul.c @@ -186,7 +186,7 @@ CASIO_LOCAL int read_picture(casio_mcsfile_t **pfile, casio_stream_t *buffer, /* read all of the pixels */ rawpxsize = casio_get_picture_size(NULL, casio_pictureformat_casemul, width, height); - rawpx = malloc(rawpxsize); + rawpx = casio_alloc(1, rawpxsize); if (!rawpx) return (casio_error_alloc); GREAD(rawpx, rawpxsize) @@ -208,7 +208,7 @@ CASIO_LOCAL int read_picture(casio_mcsfile_t **pfile, casio_stream_t *buffer, fail: if (err) casio_free_mcsfile(*pfile); *pfile = NULL; - free(rawpx); + casio_free(rawpx); return (0); } @@ -245,7 +245,7 @@ CASIO_LOCAL int read_matrix(casio_mcsfile_t **pfile, casio_stream_t *buffer, /* read double tab */ total = width * height; - tab = malloc(total * sizeof(double)); + tab = casio_alloc(total, sizeof(double)); if (!tab) return (casio_error_alloc); GREAD(tab, total * sizeof(double)) raw = tab; @@ -257,7 +257,7 @@ CASIO_LOCAL int read_matrix(casio_mcsfile_t **pfile, casio_stream_t *buffer, memcpy(head.casio_mcshead_name, name, strlen(name) + 1); head.casio_mcshead_id = name[4] - 'A' + 1; err = casio_make_mcsfile(pfile, &head); - if (err) { free(tab); return (err); } + if (err) { casio_free(tab); return (err); } /* read the matrix */ cells = (*pfile)->casio_mcsfile_cells; @@ -287,7 +287,7 @@ CASIO_LOCAL int read_matrix(casio_mcsfile_t **pfile, casio_stream_t *buffer, fail: if (err) casio_free_mcsfile(*pfile); *pfile = NULL; - free(tab); + casio_free(tab); return (0); } @@ -321,7 +321,7 @@ CASIO_LOCAL int read_list(casio_mcsfile_t **pfile, casio_stream_t *buffer, msg((ll_info, "%d elements in list", len)); /* read double tab */ - tab = malloc(len); if (!tab) return (casio_error_alloc); + tab = casio_alloc(len, 1); if (!tab) return (casio_error_alloc); GREAD(tab, len * sizeof(double)) raw = tab; @@ -332,7 +332,7 @@ CASIO_LOCAL int read_list(casio_mcsfile_t **pfile, casio_stream_t *buffer, memcpy(head.casio_mcshead_name, name, strlen(name) + 1); head.casio_mcshead_id = name[5] - '0'; err = casio_make_mcsfile(pfile, &head); - if (err) { free(tab); return (err); } + if (err) { casio_free(tab); return (err); } /* read the list */ cells = (*pfile)->casio_mcsfile_cells; @@ -362,7 +362,7 @@ CASIO_LOCAL int read_list(casio_mcsfile_t **pfile, casio_stream_t *buffer, fail: if (err) casio_free_mcsfile(*pfile); *pfile = NULL; - free(tab); + casio_free(tab); return (0); } /* ************************************************************************* */ diff --git a/src/file/decode/std.c b/src/file/decode/std.c index 0134b3f..ead01fb 100644 --- a/src/file/decode/std.c +++ b/src/file/decode/std.c @@ -115,7 +115,8 @@ int CASIO_EXPORT casio_decode_std(casio_file_t **h, const char *path, casio_uint32_t check = casio_checksum32(std, sizeof(casio_standard_header_t), 0); - /* reverse the standard header */ { + /* reverse the standard header */ + { unsigned char *u = (unsigned char*)std; size_t i; diff --git a/src/file/decode/std/eact.c.draft b/src/file/decode/std/eact.c.draft index 1e9703e..ed5a0d7 100644 --- a/src/file/decode/std/eact.c.draft +++ b/src/file/decode/std/eact.c.draft @@ -70,7 +70,7 @@ static int eact_decode_content_eact(casio_line_t *handle, uint8_t *buf, handle->casio_line_count = 0; handle->casio_line__size = count; handle->casio_line_lines = - malloc(sizeof(casio_line_t*) * handle->casio_line__size); + casio_alloc(handle->casio_line__size, sizeof(casio_line_t*)); if (!handle->casio_line_lines) return (casio_error_alloc); memset(handle->casio_line_lines, 0, sizeof(casio_line_t*) * handle->casio_line__size); @@ -82,7 +82,7 @@ static int eact_decode_content_eact(casio_line_t *handle, uint8_t *buf, be32toh(lds[0].casio_eact_line_descriptor_offset << 8); for (i = 0; i < count; i++) { /* allocate line */ - casio_line_t *line = malloc(sizeof(casio_line_t)); + casio_line_t *line = casio_alloc(1, sizeof(casio_line_t)); err = casio_error_alloc; if (!line) goto fail; @@ -122,7 +122,7 @@ static int eact_decode_content_eact(casio_line_t *handle, uint8_t *buf, loop_fail: casio_free_line_content(line); - free(line); + casio_free(line); goto fail; } @@ -310,7 +310,7 @@ static int eact_decode_line_picture(casio_line_t *handle, uint8_t *buf, if (sz == (size_t)-1) return (casio_error_magic); /* make the string */ - handle->casio_line_content = malloc(sizeof(FONTCHARACTER) * (sz + 1)); + handle->casio_line_content = casio_alloc(sz + 1, sizeof(FONTCHARACTER)); if (!handle->casio_line_content) return (casio_error_alloc); casio_wcstombs(handle->casio_line_content, s, 0); @@ -471,7 +471,7 @@ int CASIO_EXPORT casio_decode_std_eact(casio_file_t **h, hd.casio_eact_header_setup_area_size)); /* allocate handle */ - *h = malloc(sizeof(casio_file_t)); + *h = casio_alloc(1, sizeof(casio_file_t)); if (!*h) return (casio_error_alloc); casio_file_t *handle = *h; memset(handle, 0, sizeof(casio_file_t)); diff --git a/src/file/decode/std/fkey.c b/src/file/decode/std/fkey.c index ce2744a..e81a61d 100644 --- a/src/file/decode/std/fkey.c +++ b/src/file/decode/std/fkey.c @@ -88,7 +88,7 @@ int CASIO_EXPORT casio_decode_std_fkey(casio_file_t **h, data_size = be32toh(std->casio_standard_header_filesize) - sizeof(casio_standard_header_t) - sizeof(casio_fkey_subheader_t); - if (!(data = malloc(data_size))) + if (!(data = casio_alloc(data_size, 1))) goto fail; READ(data, data_size) @@ -123,7 +123,7 @@ int CASIO_EXPORT casio_decode_std_fkey(casio_file_t **h, /* omg fail! */ fail: - free(data); + casio_free(data); casio_free_file(*h); *h = NULL; return (err); } @@ -166,7 +166,7 @@ int CASIO_EXPORT casio_decode_std_cg_fkey(casio_file_t **h, - sizeof(casio_standard_subheader_t) - sizeof(casio_standard_prizm_subheader_t) - sizeof(casio_prizm_lang_subheader_t) - 4; - if (!(data = malloc(data_size))) goto fail; + if (!(data = casio_alloc(data_size, 1))) goto fail; READ(data, data_size) *check = casio_checksum32(data, data_size, *check); @@ -200,11 +200,11 @@ int CASIO_EXPORT casio_decode_std_cg_fkey(casio_file_t **h, } /* done */ - free(data); + casio_free(data); return (0); fail: - if (data) free(data); + if (data) casio_free(data); casio_free_file(*h); *h = NULL; return (err); } diff --git a/src/file/decode/std/lang.c b/src/file/decode/std/lang.c index 7c5e0e3..9f32276 100644 --- a/src/file/decode/std/lang.c +++ b/src/file/decode/std/lang.c @@ -50,7 +50,7 @@ int CASIO_EXPORT casio_decode_std_lang(casio_file_t **h, data_size = std->casio_standard_header_filesize - sizeof(casio_standard_header_t) - sizeof(casio_lang_subheader_t); - if (!(data = malloc(data_size))) goto fail; + if (!(data = casio_alloc(data_size, 1))) goto fail; READ(data, data_size) /* make the handle */ @@ -83,12 +83,12 @@ int CASIO_EXPORT casio_decode_std_lang(casio_file_t **h, } /* no error */ - free(data); + casio_free(data); return (0); /* omg fail! */ fail: - free(data); + casio_free(data); casio_free_file(*h); *h = NULL; return (err); } @@ -133,7 +133,7 @@ int CASIO_EXPORT casio_decode_std_cg_lang(casio_file_t **h, - sizeof(casio_standard_subheader_t) - sizeof(casio_standard_prizm_subheader_t) - sizeof(casio_lang_subheader_t) - 4; - if (!(data = malloc(data_size))) goto fail; + if (!(data = casio_alloc(data_size, 1))) goto fail; READ(data, data_size) *check = casio_checksum32(data, data_size, *check); @@ -167,11 +167,11 @@ int CASIO_EXPORT casio_decode_std_cg_lang(casio_file_t **h, } /* done */ - free(data); + casio_free(data); return (0); fail: - free(data); + casio_free(data); casio_free_file(*h); *h = NULL; return (err); } diff --git a/src/file/decode/std/mcs.c b/src/file/decode/std/mcs.c index 96263eb..168e78c 100644 --- a/src/file/decode/std/mcs.c +++ b/src/file/decode/std/mcs.c @@ -79,6 +79,7 @@ int CASIO_EXPORT casio_decode_std_mcs(casio_file_t **h, i, datalength)); /* decode the head */ + num--; casio_decode_mcsfile_head(&head, fhd.casio_mcs_fileheader_filetype, hd.casio_mcs_subheader_intname, diff --git a/src/file/decode/std/picture.c b/src/file/decode/std/picture.c index 5da7157..0acd5ce 100644 --- a/src/file/decode/std/picture.c +++ b/src/file/decode/std/picture.c @@ -91,7 +91,7 @@ int CASIO_EXPORT casio_decode_std_g3p(casio_file_t **h, casio_stream_t *buffer, msg((ll_info, "Reading %" CASIO_PRIuSIZE "B of deflated data", deflated_size)); err = casio_error_alloc; - if (!(defbuf = malloc(deflated_size))) goto fail; + if (!(defbuf = casio_alloc(deflated_size, 1))) goto fail; READ(defbuf, deflated_size) /* unobfuscate if required */ @@ -103,7 +103,7 @@ int CASIO_EXPORT casio_decode_std_g3p(casio_file_t **h, casio_stream_t *buffer, /* make the destination buffer */ rawsize = casio_get_picture_size(NULL, picfmt, width, height); err = casio_error_alloc; - if (!(infbuf = malloc(rawsize))) goto fail; + if (!(infbuf = casio_alloc(rawsize, 1))) goto fail; /* uncompress */ inflated_size = (uLong)rawsize; @@ -114,7 +114,7 @@ int CASIO_EXPORT casio_decode_std_g3p(casio_file_t **h, casio_stream_t *buffer, err = casio_error_magic; goto fail; } - free(defbuf); defbuf = NULL; + casio_free(defbuf); defbuf = NULL; /* check the checksum */ READ(&checksum, sizeof(casio_uint32_t)) @@ -139,7 +139,7 @@ int CASIO_EXPORT casio_decode_std_g3p(casio_file_t **h, casio_stream_t *buffer, /* then store it */ casio_decode_picture(handle->casio_file_pixels, infbuf, picfmt, handle->casio_file_width, handle->casio_file_height); - free(infbuf); infbuf = NULL; + casio_free(infbuf); infbuf = NULL; /* TODO: footers? */ @@ -147,7 +147,7 @@ int CASIO_EXPORT casio_decode_std_g3p(casio_file_t **h, casio_stream_t *buffer, return (0); fail: casio_free_file(*h); *h = NULL; - free(infbuf); free(defbuf); + casio_free(infbuf); casio_free(defbuf); return (err); } /* ************************************************************************* */ diff --git a/src/file/file.h b/src/file/file.h index b523d3d..e2db8d9 100644 --- a/src/file/file.h +++ b/src/file/file.h @@ -58,7 +58,7 @@ /* Picture utilities */ /* ************************************************************************* */ # define alloc_pixels(W, H) \ - malloc(sizeof(uint32_t*) * (H) + sizeof(uint32_t) * (W) * (H)) + casio_alloc(sizeof(uint32_t*) * (H) + sizeof(uint32_t) * (W) * (H), 1) # define prepare_pixels(I, W, H) { \ unsigned int PIXPREP_y; \ uint32_t *PIXPREP_line = (uint32_t*)&(I)[(H)]; \ diff --git a/src/file/manage.c b/src/file/manage.c index 75181fc..aa9bf48 100644 --- a/src/file/manage.c +++ b/src/file/manage.c @@ -19,7 +19,8 @@ #include "file.h" #include #define mkhandle() \ - if (!(*(h) = malloc(sizeof(casio_file_t)))) return (casio_error_alloc); \ + if (!(*(h) = casio_alloc(1, sizeof(casio_file_t)))) \ + return (casio_error_alloc); \ handle = *h; memset(handle, 0, sizeof(casio_file_t)) /* ************************************************************************* */ @@ -47,7 +48,7 @@ int CASIO_EXPORT casio_make_picture(casio_file_t **h, handle->casio_file_height = height; handle->casio_file_pixels = alloc_pixels(width, height); if (!handle->casio_file_pixels) { - free(*h); *h = NULL; return (casio_error_alloc); } + casio_free(*h); *h = NULL; return (casio_error_alloc); } prepare_pixels(handle->casio_file_pixels, width, height) /* everything went well! */ @@ -110,7 +111,7 @@ int CASIO_EXPORT casio_make_fkey(casio_file_t **h, /* allocate index */ if (count) { - handle->casio_file_fkeys = malloc(sizeof(uint32_t**) * count); + handle->casio_file_fkeys = casio_alloc(count, sizeof(uint32_t**)); if (!handle->casio_file_fkeys) goto fail; memset(handle->casio_file_fkeys, 0, sizeof(uint32_t**) * count); handle->casio_file__size = count; @@ -148,7 +149,7 @@ int CASIO_EXPORT casio_make_lang(casio_file_t **h, /* allocate index */ if (count) { - handle->casio_file_messages = malloc(sizeof(char*) * count); + handle->casio_file_messages = casio_alloc(count, sizeof(char*)); if (!handle->casio_file_messages) goto fail; memset(handle->casio_file_messages, 0, sizeof(char*) * count); handle->casio_file__size = count; @@ -202,7 +203,7 @@ int CASIO_EXPORT casio_make_addin(casio_file_t **h, handle->casio_file_size = size; /* allocate the content */ - handle->casio_file_content = malloc(size); + handle->casio_file_content = casio_alloc(size, 1); if (!handle->casio_file_content) goto fail; /* check the platform */ @@ -273,9 +274,9 @@ void CASIO_EXPORT casio_free_file(casio_file_t *handle) /* addin time! */ if (handle->casio_file_type & casio_filetype_addin) { - free(handle->casio_file_content); - free(handle->casio_file_icon_unsel); - free(handle->casio_file_icon_sel); + casio_free(handle->casio_file_content); + casio_free(handle->casio_file_icon_unsel); + casio_free(handle->casio_file_icon_sel); } /* mcs time! */ @@ -288,26 +289,26 @@ void CASIO_EXPORT casio_free_file(casio_file_t *handle) if (handle->casio_file_type & casio_filetype_lang && handle->casio_file_messages) { for (i = 0; i < handle->casio_file_count; i++) - free(handle->casio_file_messages[i]); - free(handle->casio_file_messages); + casio_free(handle->casio_file_messages[i]); + casio_free(handle->casio_file_messages); } /* function keys time! */ if (handle->casio_file_type & casio_filetype_fkey && handle->casio_file_fkeys) { for (i = 0; i < handle->casio_file_count; i++) - free(handle->casio_file_fkeys[i]); - free(handle->casio_file_fkeys); + casio_free(handle->casio_file_fkeys[i]); + casio_free(handle->casio_file_fkeys); } /* picture time! */ if (handle->casio_file_type & casio_filetype_picture) - free(handle->casio_file_pixels); + casio_free(handle->casio_file_pixels); /* e-activities time! */ /* if (handle->casio_file_type & casio_filetype_eact) casio_free_line_content(handle->casio_file_line); */ /* free the handle itself! */ - free(handle); + casio_free(handle); } diff --git a/src/link/open.c b/src/link/open.c index 49fbad3..d6beffe 100644 --- a/src/link/open.c +++ b/src/link/open.c @@ -45,7 +45,7 @@ int CASIO_EXPORT casio_open_link(casio_link_t **h, unsigned long flags, /* allocate handle */ msg((ll_info, "Allocating and building the link handle!")); *h = NULL; - if (!(*h = malloc(sizeof(casio_link_t)))) { + if (!(*h = casio_alloc(1, sizeof(casio_link_t)))) { err = casio_error_alloc; goto fail; } @@ -112,5 +112,5 @@ void CASIO_EXPORT casio_close_link(casio_link_t *handle) /* free handle */ msg((ll_info, "freeing the handle!")); - free(handle); + casio_free(handle); } diff --git a/src/link/seven/command.c b/src/link/seven/command.c index 077d5d2..e3e2d49 100644 --- a/src/link/seven/command.c +++ b/src/link/seven/command.c @@ -148,6 +148,33 @@ int CASIO_EXPORT casio_seven_send_cmd_data(casio_link_t *handle, casio_seven_type_cmd, subtype, buf, buflen, 1)); } /* ************************************************************************* */ +/* Typical MCS command */ +/* ************************************************************************* */ +/** + * casio_seven_send_typical_mcs_command: + * Send a typical MCS command. + * + * @arg handle the link handle. + * @arg code the command code. + * @arg head the MCS head. + * @arg file the file. + * @arg ow the overwrite. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_seven_send_typical_mcs_command(casio_link_t *handle, + int code, casio_mcshead_t *head, casio_mcsfile_t *file, int ow) +{ + unsigned long sz = 0; + + /* FIXME: get the file size when not NULL */ + (void)file; + return (casio_seven_send_cmd_data(handle, code, ow, + head->casio_mcshead_rawtype, sz, + head->casio_mcshead_dirname, head->casio_mcshead_name, + head->casio_mcshead_group, NULL, NULL, NULL)); +} +/* ************************************************************************* */ /* Special commands */ /* ************************************************************************* */ /** diff --git a/src/link/seven/dataflow.c b/src/link/seven/dataflow.c index 503bae0..d9530e2 100644 --- a/src/link/seven/dataflow.c +++ b/src/link/seven/dataflow.c @@ -149,8 +149,8 @@ int CASIO_EXPORT casio_seven_get_buffer(casio_link_t *handle, response.casio_seven_packet_total); /* Check if there is an overflow. */ - if (response.casio_seven_packet_data_size > size) - response.casio_seven_packet_data_size = size; + if ((casio_off_t)response.casio_seven_packet_data_size > size) + response.casio_seven_packet_data_size = (unsigned int)size; /* Copy the data. */ memcpy(p, response.casio_seven_packet_data, diff --git a/src/link/seven/datastream.c b/src/link/seven/datastream.c index 5e5f74d..cf6c1fc 100644 --- a/src/link/seven/datastream.c +++ b/src/link/seven/datastream.c @@ -20,11 +20,12 @@ * having to use temporary files or god knows what else. * ************************************************************************* */ #include "data.h" +#include "../usage/usage.h" #define BUFSIZE CASIO_SEVEN_MAX_RAWDATA_SIZE /* Cookie structure. */ typedef struct { - int _faulty; + int _faulty, _read; casio_link_t *_link; casio_link_progress_t *_disp; @@ -41,20 +42,108 @@ typedef struct { /* Callbacks */ /* ************************************************************************* */ /** - * casio_seven_data_write: - * Send data to the calculator. + * casio_seven_data_read: + * Read data from the calculator, using Protocol 7.00 data flow. * - * @arg vcookie the cookie (uncasted). + * @arg cookie the cookie. + * @arg data the data to read. + * @arg size the size of the data to read. + * @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) +{ + int err; size_t tocopy; + casio_link_t *handle = cookie->_link; + unsigned int lastsize; + + /* Check if the stream is faulty. */ + if (cookie->_faulty) + return (casio_error_noread); + + /* Empty the current buffer. */ + tocopy = cookie->_lastsize; + if (size < tocopy) tocopy = size; + if (tocopy) { + memcpy(data, &cookie->_current[cookie->_pos], tocopy); + cookie->_pos += tocopy; + data += tocopy; size -= tocopy; + + if (!size) return (0); + } + + /* Check if we have already finished. */ + if (cookie->_total && cookie->_id == cookie->_total) + return (casio_error_eof); + + /* Receive packets. */ + while (size) { + /* Send the ack and get the answer. */ + err = casio_seven_send_ack(handle, 1); + if (err) goto fail; + if (response.casio_seven_packet_type != casio_seven_type_data) { + msg((ll_error, "Packet wasn't a data packet, wtf?")); + err = casio_error_unknown; + goto fail; + } + + /* Check the total. */ + if (!cookie->_total) + cookie->_total = response.casio_seven_packet_total; + else if (cookie->_total != response.casio_seven_packet_total) { + msg((ll_error, + "Packet total did not correspond to the cached one...?")); + err = casio_error_unknown; + goto fail; + } + + /* Check the ID. */ + cookie->_id++; + if (cookie->_id != response.casio_seven_packet_id) { + msg((ll_error, "Non-consecutive data packets.")); + err = casio_error_unknown; + goto fail; + } + + /* Increment and copy. */ + lastsize = response.casio_seven_packet_data_size; + if (size >= lastsize) { + memcpy(data, response.casio_seven_packet_data, lastsize); + data += lastsize; size -= lastsize; + continue; + } + + /* Copy to the data, keep the rest! */ + cookie->_lastsize = lastsize; + memcpy(data, response.casio_seven_packet_data, size); + memcpy(&cookie->_current[size], + &response.casio_seven_packet_data[size], lastsize - size); + return (0); + } + + return (0); +fail: + /* XXX: tell the distant device we have a problem? */ + cookie->_faulty = 1; + return (err); +} + +/** + * casio_seven_data_write: + * Send data to the calculator, using Protocol 7.00 data flow. + * + * @arg cookie the cookie. * @arg data the data to write. * @arg size the size of the data to write. * @return the error code (0 if ok). */ -CASIO_LOCAL int casio_seven_data_write(void *vcookie, +CASIO_LOCAL int casio_seven_data_write(seven_data_cookie_t *cookie, const unsigned char *data, size_t size) { - seven_data_cookie_t *cookie = (void*)vcookie; int err; size_t tocopy, lastlimit; + casio_link_t *handle = cookie->_link; /* Check if the stream is faulty, or if we have already finished. */ if (cookie->_faulty) @@ -83,7 +172,7 @@ CASIO_LOCAL int casio_seven_data_write(void *vcookie, /* Send the packet. */ if (cookie->_id == 1 && cookie->_disp) (*cookie->_disp)(cookie->_disp_cookie, 1, 0); - err = casio_seven_send_quick_data_packet(cookie->_link, cookie->_total, + err = casio_seven_send_quick_data_packet(handle, cookie->_total, cookie->_id, &cookie->_reserved, cookie->_pos, 1); if (err) goto fail; if (cookie->_disp) (*cookie->_disp)(cookie->_disp_cookie, @@ -94,7 +183,7 @@ CASIO_LOCAL int casio_seven_data_write(void *vcookie, /* Intermediate packets. */ while (cookie->_id < cookie->_total && size >= BUFSIZE) { memcpy(cookie->_current, data, BUFSIZE); - err = casio_seven_send_quick_data_packet(cookie->_link, + err = casio_seven_send_quick_data_packet(handle, cookie->_total, cookie->_id, &cookie->_reserved, BUFSIZE, 1); if (err) goto fail; if (cookie->_disp) (*cookie->_disp)(cookie->_disp_cookie, @@ -110,7 +199,7 @@ CASIO_LOCAL int casio_seven_data_write(void *vcookie, /* Send the last packet if required. */ if (tocopy == lastlimit) { - err = casio_seven_send_quick_data_packet(cookie->_link, + err = casio_seven_send_quick_data_packet(handle, cookie->_total, cookie->_id, &cookie->_reserved, cookie->_pos, 1); if (err) goto fail; if (cookie->_disp) (*cookie->_disp)(cookie->_disp_cookie, @@ -135,16 +224,40 @@ fail: * casio_seven_data_close: * Close the data stream. * - * @arg vcookie the cookie (uncasted). + * @arg cookie the cookie. * @return the error code (0 if ok). */ -CASIO_LOCAL int casio_seven_data_close(void *vcookie) +CASIO_LOCAL int casio_seven_data_close(seven_data_cookie_t *cookie) { - seven_data_cookie_t *cookie = (void*)vcookie; + int err = 0; casio_link_t *handle = cookie->_link; + + /* Check if there is some data left to receive. */ + if (cookie->_read) { + if (!cookie->_total) { + err = casio_seven_send_ack(handle, 1); + if (err) goto fail; + + cookie->_id = response.casio_seven_packet_id; + cookie->_total = response.casio_seven_packet_total; + if (cookie->_id != 1) { err = casio_error_unknown; goto fail; } + } + + while (cookie->_id < cookie->_total) { + err = casio_seven_send_ack(handle, 1); + if (err) goto fail; + + if (cookie->_id + 1 != response.casio_seven_packet_id + || cookie->_total != response.casio_seven_packet_total) { + err = casio_error_unknown; + goto fail; + } + cookie->_id++; + } + } /* Check if there is some data left to send. */ - if (cookie->_id <= cookie->_total) { + if (!cookie->_read && cookie->_id <= cookie->_total) { size_t left; unsigned char zeroes[BUFSIZE]; /* Intermediate packets. */ @@ -163,22 +276,24 @@ CASIO_LOCAL int casio_seven_data_close(void *vcookie) * go directly to the end. */ memset(zeroes, 0, BUFSIZE); for (; left >= BUFSIZE; left -= BUFSIZE) { - if (casio_seven_data_write(vcookie, zeroes, BUFSIZE)) - goto end; + if ((err = casio_seven_data_write(cookie, zeroes, BUFSIZE))) + goto fail; } - casio_seven_data_write(vcookie, zeroes, left); + + err = casio_seven_data_write(cookie, zeroes, left); } -end: - free(vcookie); - return (0); + err = 0; +fail: + casio_free(cookie); + return (err); } /* ************************************************************************* */ /* Opening functions */ /* ************************************************************************* */ CASIO_LOCAL const casio_streamfuncs_t seven_data_callbacks = casio_stream_callbacks_for_virtual(casio_seven_data_close, - NULL, casio_seven_data_write, NULL); + casio_seven_data_read, casio_seven_data_write, NULL); /** * casio_seven_open_data_stream: @@ -197,23 +312,42 @@ int CASIO_EXPORT casio_seven_open_data_stream(casio_stream_t **stream, void *dcookie) { seven_data_cookie_t *cookie = NULL; + casio_mode_t mode; - /* XXX: args checks */ + /* make checks */ + chk_handle(link); + chk_seven(link); /* make the cookie */ - cookie = malloc(sizeof(cookie)); + cookie = casio_alloc(1, sizeof(seven_data_cookie_t)); if (!cookie) return (casio_error_alloc); + + /* initialize the cookie and mode */ cookie->_faulty = 0; cookie->_link = link; + cookie->_pos = 0; cookie->_disp = disp; cookie->_disp_cookie = dcookie; - cookie->_id = 1; - cookie->_lastsize = (unsigned int)(size % BUFSIZE); - cookie->_total = (unsigned int)(size / BUFSIZE) + !!cookie->_lastsize; - if (!cookie->_lastsize) cookie->_lastsize = BUFSIZE; - cookie->_pos = 0; + if (link->casio_link_flags & casio_linkflag_active) { + msg((ll_info, "The data stream is a write one.")); + mode = CASIO_OPENMODE_WRITE; + + cookie->_read = 0; + cookie->_id = 1; + cookie->_total = (unsigned int)(size / BUFSIZE) + !!cookie->_lastsize; + cookie->_lastsize = (unsigned int)(size % BUFSIZE); + if (!cookie->_lastsize) cookie->_lastsize = BUFSIZE; + } else { + msg((ll_info, "The data stream is a read one.")); + mode = CASIO_OPENMODE_READ; + + cookie->_read = 1; + cookie->_id = 0; + cookie->_total = 0; + cookie->_lastsize = 0; + } /* initialize the stream */ - return (casio_open(stream, CASIO_OPENMODE_WRITE, 0, cookie, + return (casio_open(stream, mode, 0, cookie, &seven_data_callbacks)); } diff --git a/src/link/seven/send.c b/src/link/seven/send.c index a9884df..f22d24d 100644 --- a/src/link/seven/send.c +++ b/src/link/seven/send.c @@ -91,10 +91,6 @@ CASIO_LOCAL int casio_seven_send_buf(casio_link_t *handle, /* send prepared packet */ err = casio_write(handle->casio_link_stream, buf, bufsize); if (err) return (err); -#if 0 /* FIXME */ - if (handle->casio_link_last_type == casio_seven_type_swp) - handle->casio_link_flags &= ~casio_linkflag_ended; -#endif /* set wasreset for logging */ wasresend = 1; @@ -110,6 +106,8 @@ CASIO_LOCAL int casio_seven_send_buf(casio_link_t *handle, } /* packet sending is finished */ + if (!resp_err && handle->casio_link_curr_type == casio_seven_type_swp) + handle->casio_link_flags &= ~casio_linkflag_active; return (resp_err); } diff --git a/src/link/seven_mcs/delete.c b/src/link/seven_mcs/delete.c new file mode 100644 index 0000000..7c897a8 --- /dev/null +++ b/src/link/seven_mcs/delete.c @@ -0,0 +1,50 @@ +/* **************************************************************************** + * link/seven_mcs/delete.c -- delete a file on a Protocol 7.00 main memory. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "seven_mcs.h" + +/** + * casio_sevenmcs_delete: + * Delete a file on the link main memory. + * + * @arg cookie the link main memory cookie. + * @arg mcshead the head of the file to delete. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_sevenmcs_delete(sevenmcs_t *cookie, + casio_mcshead_t *mcshead) +{ + int err; casio_link_t *handle = cookie->sevenmcs_link; + casio_mcshead_t head; + + msg((ll_info, "Correcting the head.")); + memcpy(&head, mcshead, sizeof(head)); + if (casio_correct_mcshead(&head, casio_mcsfor_mcs)) + return (casio_error_notfound); + + msg((ll_info, "Sending the deletion command.")); + err = casio_seven_send_cmdmcs_delfile(handle, &head); + if (err) return (err); + if (response.casio_seven_packet_type == casio_seven_type_nak) + return (casio_error_notfound); + if (response.casio_seven_packet_type != casio_seven_type_ack) + return (casio_error_unknown); + + return (0); +} diff --git a/src/link/seven_mcs/get.c b/src/link/seven_mcs/get.c new file mode 100644 index 0000000..e5081a6 --- /dev/null +++ b/src/link/seven_mcs/get.c @@ -0,0 +1,123 @@ +/* **************************************************************************** + * link/seven_mcs/get.c -- get a file from a protocol seven main memory. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "seven_mcs.h" + +struct thecookie { + int _called; + int _err; + casio_mcshead_t *_head; + casio_mcsfile_t **_mcsfile; + casio_link_progress_t *_disp; + void *_disp_cookie; +}; + +/** + * get_file: + * Get the main memory file. + * + * @arg cookie the cookie (uncasted). + * @arg handle the link handle. + * @return the error code (0 if ok). + */ + +CASIO_LOCAL int get_file(struct thecookie *cookie, casio_link_t *handle) +{ + casio_stream_t *data_stream = NULL; + casio_mcshead_t *head = cookie->_head; + + /* Check if the callback is already called. */ + if (cookie->_called) + return (casio_error_unknown); + cookie->_called = 1; + + /* Correct the head. */ + head->casio_mcshead_size = response.casio_seven_packet_filesize; + + /* Make the data stream. */ + cookie->_err = casio_seven_open_data_stream(&data_stream, handle, 0, + cookie->_disp, cookie->_disp_cookie); + if (cookie->_err) return (casio_error_unknown); + + /* Decode the MCS file. */ + cookie->_err = casio_decode_mcsfile(cookie->_mcsfile, head, data_stream); + casio_close(data_stream); + if (cookie->_err) return (casio_error_unknown); + + /* Send the final ack and return. */ + return (casio_seven_send_ack(handle, 1)); +} + +/** + * casio_sevenmcs_get: + * Get a file from a Protocol 7.00 main memory interface. + * + * @arg cookie the interface cookie. + * @arg mcsfile the MCS file to get. + * @arg mcshead the MCS head. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_sevenmcs_get(sevenmcs_t *cookie, + casio_mcsfile_t **mcsfile, casio_mcshead_t *mcshead) +{ + int err; casio_mcshead_t head; + casio_link_t *handle = cookie->sevenmcs_link; + struct thecookie ccookie; + + /* Correct the head. */ + msg((ll_info, "Correcting the head.")); + memcpy(&head, mcshead, sizeof(head)); + if (casio_correct_mcshead(&head, casio_mcsfor_mcs)) + return (casio_error_notfound); + + /* Send the command. */ + msg((ll_info, "Sending the file request.")); + err = casio_seven_send_cmd_data(handle, + casio_seven_cmdmcs_reqfile, 0, head.casio_mcshead_rawtype, 0, + head.casio_mcshead_dirname, head.casio_mcshead_name, + head.casio_mcshead_group, NULL, NULL, NULL); + if (err) return (err); + + /* Check the answer. */ + if (response.casio_seven_packet_type == casio_seven_type_nak + && response.casio_seven_packet_code == casio_seven_err_other) + return (casio_error_notfound); + else if (response.casio_seven_packet_type != casio_seven_type_ack) + return (casio_error_unknown); + + /* Prepare the cookie. */ + ccookie._called = 0; + ccookie._err = 0; + ccookie._mcsfile = mcsfile; + ccookie._head = &head; + ccookie._disp = NULL; + ccookie._disp_cookie = NULL; + + msg((ll_info, "Preparing the callbacks and running the server.")); + memset(handle->casio_link_seven_callbacks, 0, + 256 * sizeof(casio_seven_server_func_t*)); + handle->casio_link_seven_callbacks[casio_seven_cmdmcs_sendfile] = + (casio_seven_server_func_t*)&get_file; + err = casio_seven_serve(handle, handle->casio_link_seven_callbacks, + &ccookie); + if (err) return (err); + + /* Check if the function was called. */ + return (ccookie._called ? ccookie._err : casio_error_unknown); +} diff --git a/src/link/seven_mcs/list.c b/src/link/seven_mcs/list.c new file mode 100644 index 0000000..bd321ae --- /dev/null +++ b/src/link/seven_mcs/list.c @@ -0,0 +1,95 @@ +/* **************************************************************************** + * link/seven_mcs/list.c -- list files on a protocol seven main memory. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "seven_mcs.h" + +struct thecookie { + casio_mcslist_t *_mcslist; + void *_mcookie; +}; + +/** + * file_info: + * The file information callback. + * + * @arg cookie the cookie. + * @arg handle the link handle. + * @return the error code (0 if ok). + */ + +CASIO_LOCAL int file_info(struct thecookie *cookie, casio_link_t *handle) +{ + casio_mcshead_t head; + + /* Copy the raw information. */ + head.casio_mcshead_flags = casio_mcsfor_mcs; + head.casio_mcshead_size = response.casio_seven_packet_filesize; + head.casio_mcshead_rawtype = response.casio_seven_packet_mcstype; + strncpy(head.casio_mcshead_dirname, + response.casio_seven_packet_args[0], 8); + head.casio_mcshead_dirname[8] = 0; + strncpy(head.casio_mcshead_name, + response.casio_seven_packet_args[1], 12); + head.casio_mcshead_name[12] = 0; + strncpy(head.casio_mcshead_group, + response.casio_seven_packet_args[2], 16); + head.casio_mcshead_group[16] = 0; + + /* Try to make abstract information out of the raw information. */ + casio_correct_mcshead(&head, 0); + + /* Return this head to the user, and end the command response. */ + (*cookie->_mcslist)(cookie->_mcookie, &head); + return (0); +} + +/** + * casio_sevenmcs_list: + * List a Protocol 7.00 MCS. + * + * @arg cookie the cookie. + * @arg mcslist the listing callback. + * @arg mcookie the listing callback cookie. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_sevenmcs_list(sevenmcs_t *cookie, + casio_mcslist_t *mcslist, void *mcookie) +{ + int err; casio_link_t *handle = cookie->sevenmcs_link; + struct thecookie thecookie; + + msg((ll_info, "Sending the file info transfer all request.")); + err = casio_seven_send_cmdmcs_reqallinfo(handle); + if (err) return (err); + if (response.casio_seven_packet_type != casio_seven_type_ack) + return (casio_error_unknown); + + /* Prepare the cookie. */ + thecookie._mcslist = mcslist; + thecookie._mcookie = mcookie; + + msg((ll_info, "Preparing the callbacks and running the server.")); + memset(handle->casio_link_seven_callbacks, 0, + 256 * sizeof(casio_seven_server_func_t*)); + handle->casio_link_seven_callbacks[casio_seven_cmdmcs_fileinfo] = + (casio_seven_server_func_t*)&file_info; + err = casio_seven_serve(handle, handle->casio_link_seven_callbacks, + &thecookie); + return (err); +} diff --git a/src/link/seven_mcs/open.c b/src/link/seven_mcs/open.c new file mode 100644 index 0000000..7d04cce --- /dev/null +++ b/src/link/seven_mcs/open.c @@ -0,0 +1,73 @@ +/* **************************************************************************** + * link/seven_mcs/open.c -- open a protocol seven MCS interface. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "seven_mcs.h" + +/* ************************************************************************* */ +/* Close callback */ +/* ************************************************************************* */ +/** + * casio_sevenmcs_close: + * Close a Protocol 7.00 MCS cookie. + * + * @arg cookie the cookie. + * @return the error code (0 if ok). + */ + +CASIO_LOCAL int casio_sevenmcs_close(sevenmcs_t *cookie) +{ + /* XXX: should we close the link or something? */ + casio_free(cookie); + return (0); +} + +/* Callbacks. */ +CASIO_LOCAL casio_mcsfuncs_t seven_mcs_funcs = { + (casio_mcs_get_t*)&casio_sevenmcs_get, +/* (casio_mcs_put_t*)&casio_sevenmcs_put, */ NULL, + (casio_mcs_delete_t*)&casio_sevenmcs_delete, + (casio_mcs_list_t*)&casio_sevenmcs_list, + (casio_mcs_close_t*)&casio_sevenmcs_close}; +/* ************************************************************************* */ +/* Main opening function */ +/* ************************************************************************* */ +/** + * casio_open_seven_mcs: + * Open a Protocol 7.00 MCS interface. + * + * @arg mcs the interface to open. + * @arg link the link. + */ + +int CASIO_EXPORT casio_open_seven_mcs(casio_mcs_t **mcs, casio_link_t *link) +{ + int err; sevenmcs_t *cookie = NULL; + + /* Allocate the cookie. */ + cookie = casio_alloc(1, sizeof(sevenmcs_t)); + if (!cookie) return (casio_error_alloc); + cookie->sevenmcs_link = link; + + /* Make the main memory. */ + err = casio_open_mcs(mcs, cookie, &seven_mcs_funcs); + if (err) return (err); + + /* We're done! */ + msg((ll_info, "The link MCS is open!")); + return (0); +} diff --git a/src/link/seven_mcs/put.c.draft b/src/link/seven_mcs/put.c.draft new file mode 100644 index 0000000..9423f5e --- /dev/null +++ b/src/link/seven_mcs/put.c.draft @@ -0,0 +1,61 @@ +/* **************************************************************************** + * link/seven_mcs/put.c -- put a file into a protocol seven main memory. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "seven_mcs.h" + +/** + * casio_sevenmcs_put: + * Put the file to the Protocol 7.00 main memory. + * + * @arg cookie the Protocol 7.00 main memory interface detail. + * @arg mcsfile the MCS file to send. + * @return the error code (0 if ok). + */ + +int casio_sevenmcs_put(sevenmcs_t *cookie, casio_mcsfile_t *mcsfile) +{ + int err; casio_mcshead_t *head; + casio_stream_t *data_stream; + + /* Send the command. */ + msg((ll_info, "Sending the file request.")); + err = casio_seven_send_cmd_data(cookie->sevenmcs_link, + casio_seven_cmdmcs_putfile, casio_seven_ow_force, + head.casio_mcshead_rawtype, /* FIXME: size */, + head.casio_mcshead_dirname, head.casio_mcshead_name, + head.casio_mcshead_group, NULL, NULL, NULL); + if (err) return (err); + + /* Check the answer. */ + if (response.casio_seven_packet_type == casio_seven_type_nak + && response.casio_seven_packet_code == casio_seven_err_other) + return (casio_error_op); + else if (response.casio_seven_packet_type != casio_seven_type_ack) + return (casio_error_unknown); + + /* Make the data stream. */ + err = casio_seven_open_data_stream(&data_stream, cookie->sevenmcs_link, + /* FIXME: size */, cookie->sevenmcs_disp, + cookie->sevenmcs_disp_cookie); + if (err) return (err); + + /* Encode the file on-the-flight. */ + err = casio_encode_mcsfile(mcsfile, data_stream); + casio_close(data_stream); + return (err); +} diff --git a/src/link/seven_mcs/seven_mcs.h b/src/link/seven_mcs/seven_mcs.h new file mode 100644 index 0000000..f7added --- /dev/null +++ b/src/link/seven_mcs/seven_mcs.h @@ -0,0 +1,41 @@ +/* **************************************************************************** + * link/seven_mcs/seven_mcs.h -- protocol seven MCS interface internals. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#ifndef LINK_SEVEN_MCS_H +# define LINK_SEVEN_MCS_H 1 +# include "../usage/usage.h" + +typedef struct { + casio_link_t *sevenmcs_link; +} sevenmcs_t; + +CASIO_EXTERN int CASIO_EXPORT casio_sevenmcs_get + OF((sevenmcs_t *casio__cookie, casio_mcsfile_t **casio__mcsfile, + casio_mcshead_t *casio__head)); + +CASIO_EXTERN int CASIO_EXPORT casio_sevenmcs_put + OF((sevenmcs_t *casio__cookie, casio_mcsfile_t *casio__mcsfile)); + +CASIO_EXTERN int CASIO_EXPORT casio_sevenmcs_delete + OF((sevenmcs_t *casio__cookie, casio_mcshead_t *casio__mcshead)); + +CASIO_EXTERN int CASIO_EXPORT casio_sevenmcs_list + OF((sevenmcs_t *casio__cookie, casio_mcslist_t *casio__mcslist, + void *casio__mcslist_cookie)); + +#endif /* LINK_SEVEN_MCS_H */ diff --git a/src/link/usage/backup_rom.c b/src/link/usage/backup_rom.c index 8d46f15..d9aad0d 100644 --- a/src/link/usage/backup_rom.c +++ b/src/link/usage/backup_rom.c @@ -31,7 +31,7 @@ struct thecookie { * * @arg vcookie the cookie (uncasted). * @arg handle the link handle. - * @return the return thingy. + * @return the error code (0 if ok). */ CASIO_LOCAL int get_rom(void *vcookie, casio_link_t *handle) diff --git a/src/link/usage/getscreen.c b/src/link/usage/getscreen.c index 9d5ef0b..f67b05c 100644 --- a/src/link/usage/getscreen.c +++ b/src/link/usage/getscreen.c @@ -44,8 +44,8 @@ int CASIO_EXPORT casio_getscreen(casio_link_t *handle, chk_passive(handle); /* allocate pixels. */ - pixels = malloc(sizeof(uint32_t*) * HEIGHT - + sizeof(uint32_t) * WIDTH * HEIGHT); + pixels = casio_alloc(sizeof(uint32_t*) * HEIGHT + + sizeof(uint32_t) * WIDTH * HEIGHT, 1); if (!pixels) failure(alloc); /* prepare pixels. */ @@ -73,6 +73,6 @@ int CASIO_EXPORT casio_getscreen(casio_link_t *handle, err = 0; fail: - free(pixels); + casio_free(pixels); return (0); } diff --git a/src/link/usage/server/seven.c b/src/link/usage/server/seven.c index 182edb3..2822de9 100644 --- a/src/link/usage/server/seven.c +++ b/src/link/usage/server/seven.c @@ -57,8 +57,9 @@ int CASIO_EXPORT casio_seven_serve(casio_link_t *handle, while (1) { /* Check command packet. */ if (response.casio_seven_packet_type != casio_seven_type_cmd) { - if (response.casio_seven_packet_type == casio_seven_type_end - || response.casio_seven_packet_type == casio_seven_type_swp) + if (response.casio_seven_packet_type == casio_seven_type_end) + return (casio_seven_send_ack(handle, 0)); + if (response.casio_seven_packet_type == casio_seven_type_swp) break; err = casio_seven_send_err(handle, casio_seven_err_other); @@ -83,5 +84,5 @@ int CASIO_EXPORT casio_seven_serve(casio_link_t *handle, } /* Ack and disconnect. */ - return (casio_seven_send_ack(handle, 0)); + return (0); } diff --git a/src/log/manage.c b/src/log/manage.c index 09a3b51..175a99d 100644 --- a/src/log/manage.c +++ b/src/log/manage.c @@ -122,5 +122,6 @@ void CASIO_EXPORT casio_listlog(casio_log_list_t *callback, void *cookie) int CASIO_EXPORT casio_islog(casio_loglevel_t level, const char *func) { + (void)func; return (islog(level)); } diff --git a/src/mcs/local/find.c b/src/mcs/local/find.c index e605504..6727f69 100644 --- a/src/mcs/local/find.c +++ b/src/mcs/local/find.c @@ -68,7 +68,7 @@ int CASIO_EXPORT casio_localmcs_find(localmcs_t *cookie, casio_mcsfile_t **newindex = NULL; /* Allocate the new index. */ - newindex = malloc(newsize * sizeof(casio_mcsfile_t*)); + newindex = casio_alloc(newsize, sizeof(casio_mcsfile_t*)); if (!newindex) return (casio_error_alloc); /* Copy the old index data. */ @@ -81,7 +81,7 @@ int CASIO_EXPORT casio_localmcs_find(localmcs_t *cookie, (newsize - cookie->localmcs_size) * sizeof(casio_mcsfile_t*)); /* Free the old index, assign the new one. */ - free(cookie->localmcs_files); + casio_free(cookie->localmcs_files); cookie->localmcs_files = newindex; cookie->localmcs_size = newsize; } diff --git a/src/mcs/local/list.c b/src/mcs/local/list.c index abce816..f12f8a2 100644 --- a/src/mcs/local/list.c +++ b/src/mcs/local/list.c @@ -30,7 +30,7 @@ int CASIO_EXPORT casio_localmcs_list(localmcs_t *cookie, casio_mcslist_t *mcslist, void *mcookie) { - int err, i, count = cookie->localmcs_count; + int i, count = cookie->localmcs_count; for (i = 0; count && i < cookie->localmcs_size; i++) { casio_mcsfile_t *file = cookie->localmcs_files[i]; @@ -42,8 +42,7 @@ int CASIO_EXPORT casio_localmcs_list(localmcs_t *cookie, count--; /* Call back the callback. */ - err = (*mcslist)(mcookie, &file->casio_mcsfile_head); - if (err) return (err); + (*mcslist)(mcookie, &file->casio_mcsfile_head); } /* Everything went well :) */ diff --git a/src/mcs/local/local.h b/src/mcs/local/local.h index 51d081e..9aa52dc 100644 --- a/src/mcs/local/local.h +++ b/src/mcs/local/local.h @@ -41,13 +41,13 @@ CASIO_EXTERN int CASIO_EXPORT casio_localmcs_get casio_mcshead_t *casio__head)); CASIO_EXTERN int CASIO_EXPORT casio_localmcs_put - OF((localmcs_t *casio__cookie, casio_mcsfile_t *casio__mcsfile)); + OF((localmcs_t *casio__cookie, casio_mcsfile_t *casio__mcsfile)); CASIO_EXTERN int CASIO_EXPORT casio_localmcs_delete - OF((localmcs_t *casio__cookie, casio_mcshead_t *casio__mcshead)); + OF((localmcs_t *casio__cookie, casio_mcshead_t *casio__mcshead)); CASIO_EXTERN int CASIO_EXPORT casio_localmcs_list - OF((localmcs_t *casio__cookie, casio_mcslist_t *casio__mcslist, + OF((localmcs_t *casio__cookie, casio_mcslist_t *casio__mcslist, void *casio__mcslist_cookie)); #endif /* LOCAL_MCS_LOCAL_H */ diff --git a/src/mcs/local/open.c b/src/mcs/local/open.c index 201997f..9e1b3b2 100644 --- a/src/mcs/local/open.c +++ b/src/mcs/local/open.c @@ -31,8 +31,16 @@ CASIO_LOCAL int casio_localmcs_close(localmcs_t *cookie) { - free(cookie->localmcs_files); - free(cookie); + int i, count = cookie->localmcs_count; + + /* Free the files. */ + for (i = 0; count && i < cookie->localmcs_size; i++) { + if (!cookie->localmcs_files[i]) continue; + casio_free_mcsfile(cookie->localmcs_files[i]); + } + + /* Free the index and the cookie. */ + casio_free(cookie->localmcs_files); casio_free(cookie); return (0); } @@ -59,12 +67,12 @@ int CASIO_EXPORT casio_open_local_mcs(casio_mcs_t **mcs) localmcs_t *cookie = NULL; /* Allocate the cookie. */ - cookie = malloc(sizeof(*cookie)); + cookie = casio_alloc(1, sizeof(*cookie)); if (!cookie) return (casio_error_alloc); cookie->localmcs_count = 0; cookie->localmcs_size = 0; cookie->localmcs_files = NULL; - /* Make the filesystem. */ + /* Make the main memory. */ return (casio_open_mcs(mcs, cookie, &funcs)); } diff --git a/src/mcs/open.c b/src/mcs/open.c index 9ae0412..f5ec583 100644 --- a/src/mcs/open.c +++ b/src/mcs/open.c @@ -34,7 +34,7 @@ int CASIO_EXPORT casio_open_mcs(casio_mcs_t **m, void *cookie, int err; casio_mcs_t *mcs = NULL; /* Allocate the filesystem. */ - *m = malloc(sizeof(casio_mcs_t)); mcs = *m; + *m = casio_alloc(1, sizeof(casio_mcs_t)); mcs = *m; if (!mcs) { err = casio_error_alloc; goto fail; } /* Set it up and return it. */ @@ -61,6 +61,6 @@ int CASIO_EXPORT casio_close_mcs(casio_mcs_t *mcs) if (!mcs || !(func = mcs->casio_mcs_funcs.casio_mcsfuncs_close)) return (0); err = (*func)(mcs->casio_mcs_cookie); - free(mcs); + casio_free(mcs); return (err); } diff --git a/src/mcsfile/decode/cas.c b/src/mcsfile/decode/cas.c index 8c82809..a698b13 100644 --- a/src/mcsfile/decode/cas.c +++ b/src/mcsfile/decode/cas.c @@ -20,6 +20,7 @@ * https://casetta.tuxfamily.org/formats/cas * ************************************************************************* */ #include "decode.h" +#include "../reference/reference.h" #define FUNC(NAME) &casio_decode_caspart_##NAME #define HFUNC(NAME) &casio_decode_cashpart_##NAME @@ -93,11 +94,11 @@ CASIO_LOCAL int decode_cas50(casio_mcshead_t *head, casio_stream_t *buffer, /* read the raw header */ DREAD(hd) msg((ll_info, "Raw CAS50 (CASPRO) header content (app: '%.3s'):", - head->casio_mcshead_appname)); + head->casio_mcshead_cas_app)); mem((ll_info, &hd, sizeof(casio_cas50_t))); /* check the checksum */ - csum = casio_checksum_cas(&hd, sizeof(casio_cas50_t) - 1, 0); + csum = casio_checksum_cas(&hd, sizeof(casio_cas50_t) - 1, csum); if (csum != hd.casio_cas50_checksum) { msg((ll_error, "Checksum mismatch: expected 0x%02X, got 0x%02X", hd.casio_cas50_checksum, csum)); @@ -105,7 +106,9 @@ CASIO_LOCAL int decode_cas50(casio_mcshead_t *head, casio_stream_t *buffer, } /* copy the basic information */ - casio_maketype_cas(head, (char*)hd.casio_cas50_data); + head->casio_mcshead_flags = casio_mcsfor_cas50; + memcpy(head->casio_mcshead_datatype, hd.casio_cas50_data, 2); + casio_correct_mcshead(head, 0); head->casio_mcshead_size = be16toh(hd.casio_cas50_height) - 2 /* checksum, colon */; end = memchr(hd.casio_cas50_name, 0xFF, 8); @@ -162,17 +165,27 @@ int CASIO_EXPORT casio_decode_casfile_head(casio_mcshead_t *head, /* read beginning of the header, check if is an extended header */ READ(buf, 4) csum = casio_checksum_cas(buf, 4, 0); - if (!casio_maketype_casapp(head, dhd->casio_casdyn_ext, - (char*)dhd->casio_casdyn_app)) - switch (head->casio_mcshead_flags & casio_mcsfor_mask) { - case casio_mcsfor_cas50: return (decode_cas50(head, buffer, csum)); + if (!casio_check_cas_app(dhd->casio_casdyn_ext, + (char*)dhd->casio_casdyn_app)) { + memcpy(head->casio_mcshead_cas_app, dhd->casio_casdyn_app, 3); + head->casio_mcshead_cas_app[3] = 0; + head->casio_mcshead_cas_ext = dhd->casio_casdyn_ext; + + switch (dhd->casio_casdyn_ext) { + case casio_casdyn_9850: /* FALLTHRU */ + case casio_casdyn_end: + return (decode_cas50(head, buffer, csum)); + #if 0 - case casio_mcsfor_cas100: return (decode_cas100(head, buffer)); + case casio_casdyn_g100: /* FALLTHRU */ + case casio_casdyn_g100b: + return (decode_cas100(head, buffer)); #endif default: msg((ll_error, "Platform 0x%08X isn't implemented yet.", head->casio_mcshead_flags & casio_mcsfor_mask)); return (casio_error_op); + } } /* is a CAS40 head, read it. */ @@ -180,7 +193,9 @@ int CASIO_EXPORT casio_decode_casfile_head(casio_mcshead_t *head, csum = casio_checksum_cas(&buf[4], 34, csum); msg((ll_info, "Raw CAS40 (CAS) header:")); mem((ll_info, hd, sizeof(casio_cas40_t))); - if (casio_maketype_cas(head, (char*)hd->casio_cas40_data)) + head->casio_mcshead_flags = casio_mcsfor_cas40; + memcpy(head->casio_mcshead_datatype, hd->casio_cas40_data, 2); + if (casio_correct_mcshead(head, 0)) return (casio_error_magic); if (~csum + 1 != hd->casio_cas40_checksum) return (casio_error_csum); diff --git a/src/mcsfile/decode/cas/screenshot.c b/src/mcsfile/decode/cas/screenshot.c index 15e352d..7aceafa 100644 --- a/src/mcsfile/decode/cas/screenshot.c +++ b/src/mcsfile/decode/cas/screenshot.c @@ -42,7 +42,8 @@ int CASIO_EXPORT casio_decode_caspart_capture(casio_mcsfile_t *handle, /* read the picture size */ err = casio_error_alloc; - pic_data = malloc(pic_size); if (!pic_data) return (err); + pic_data = casio_alloc(pic_size, 1); + if (!pic_data) return (err); GREAD(pic_data, pic_size) /* decode the picture data */ @@ -57,6 +58,6 @@ int CASIO_EXPORT casio_decode_caspart_capture(casio_mcsfile_t *handle, err = 0; fail: if (err) casio_free_mcsfile(handle); - free(pic_data); + casio_free(pic_data); return (0); } diff --git a/src/mcsfile/decode/mcs.c b/src/mcsfile/decode/mcs.c index 8a4faeb..799c8e6 100644 --- a/src/mcsfile/decode/mcs.c +++ b/src/mcsfile/decode/mcs.c @@ -86,15 +86,24 @@ CASIO_LOCAL mcs_decode_func_t *lookup_mcsfile_decode(casio_mcstype_t type) int CASIO_EXPORT casio_decode_mcsfile_head(casio_mcshead_t *head, int raw_type, const unsigned char *groupname, const unsigned char *dirname, const unsigned char *filename, - uint_fast32_t filesize) + unsigned long filesize) { /* check that we have a head, lol */ if (!head) return (-1); - /* look for the raw type */ - casio_maketype_mcs(head, (char*)groupname, (char*)dirname, - (char*)filename, raw_type); + /* prepare the head */ + head->casio_mcshead_flags = casio_mcsfor_mcs; head->casio_mcshead_size = filesize; + head->casio_mcshead_rawtype = raw_type; + strncpy(head->casio_mcshead_name, (char*)filename, 12); + head->casio_mcshead_name[12] = 0; + strncpy(head->casio_mcshead_group, (char*)groupname, 16); + head->casio_mcshead_group[16] = 0; + strncpy(head->casio_mcshead_dirname, (char*)dirname, 8); + head->casio_mcshead_dirname[8] = 0; + + /* make the lib abstract types out of this raw information. */ + casio_correct_mcshead(head, 0); msg((ll_info, "libcasio file type is 0x%08lX", head->casio_mcshead_type)); ifmsg(casio_mcshead_uses_id(head), (ll_info, @@ -141,18 +150,26 @@ int CASIO_EXPORT casio_decode_mcsfile(casio_mcsfile_t **handle, } /* decode */ - if (!head->casio_mcshead_size) err = (*decode)(handle, buffer, &h); + if (!head->casio_mcshead_size) + err = (*decode)(handle, buffer, &h); else { casio_stream_t *lbuf; int alterr; + /* Open the limited buffer. */ + msg((ll_info, "Making a limited buffer out of the buffer.")); err = casio_open_limited(&lbuf, buffer, head->casio_mcshead_size); if (err) goto fail; + + /* Call the decode error. */ + msg((ll_info, "Decoding the file with the specific function.")); err = (*decode)(handle, lbuf, &h); alterr = casio_empty_limited(lbuf); casio_close(lbuf); - if (!err && alterr) err = alterr; - if (err) goto fail; + + /* Check the error. */ + if (!err && alterr) + err = alterr; } /* oh yeah, and go away. */ @@ -175,7 +192,7 @@ notparsing: return (0); fail: - casio_free_mcsfile(*handle); + casio_free_mcsfile(*handle); *handle = NULL; return (err); } diff --git a/src/mcsfile/decode/mcs/picture.c b/src/mcsfile/decode/mcs/picture.c index 474b47a..e1cbca2 100644 --- a/src/mcsfile/decode/mcs/picture.c +++ b/src/mcsfile/decode/mcs/picture.c @@ -55,7 +55,7 @@ int CASIO_EXPORT casio_decode_mcs_capture(casio_mcsfile_t **h, pic_size = casio_get_picture_size(NULL, casio_pictureformat_1bit_packed, head->casio_mcshead_width, head->casio_mcshead_height); err = casio_error_alloc; - if (!(pic_raw = malloc(pic_size))) goto fail; + if (!(pic_raw = casio_alloc(pic_size, 1))) goto fail; READ(pic_raw, pic_size) /* get the image and return */ @@ -65,10 +65,10 @@ int CASIO_EXPORT casio_decode_mcs_capture(casio_mcsfile_t **h, goto fail; /* no error! */ - free(pic_raw); + casio_free(pic_raw); return (0); fail: - free(pic_raw); + casio_free(pic_raw); casio_free_mcsfile(*h); *h = NULL; return (err); @@ -102,7 +102,7 @@ int CASIO_EXPORT casio_decode_mcs_picture(casio_mcsfile_t **h, pic_size = casio_get_picture_size(NULL, casio_pictureformat_1bit_packed, head->casio_mcshead_width, head->casio_mcshead_height); err = casio_error_alloc; - if (!(pics_raw = malloc(pic_size * 2))) goto fail; + if (!(pics_raw = casio_alloc(pic_size * 2, 1))) goto fail; READ(pics_raw, pic_size * 2) /* decode the images */ @@ -115,10 +115,10 @@ int CASIO_EXPORT casio_decode_mcs_picture(casio_mcsfile_t **h, goto fail; /* no error */ - free(pics_raw); + casio_free(pics_raw); return (0); fail: casio_free_mcsfile(*h); *h = NULL; - free(pics_raw); + casio_free(pics_raw); return (0); } diff --git a/src/mcsfile/decode/mcs/spreadsheet.c b/src/mcsfile/decode/mcs/spreadsheet.c index f71a6a8..8c76016 100644 --- a/src/mcsfile/decode/mcs/spreadsheet.c +++ b/src/mcsfile/decode/mcs/spreadsheet.c @@ -53,7 +53,7 @@ int CASIO_EXPORT casio_decode_mcs_spreadsheet(casio_mcsfile_t **h, be32toh(shd.casio_mcs_spreadsheet_subheader_defs_size); /* prepare */ - cells = malloc(sizeof(casio_mcscell_t) * 1000 * colcount); + cells = casio_alloc(1000 * colcount, sizeof(casio_mcscell_t)); memset(cells, 0, sizeof(casio_mcscell_t) * 1000 * colcount); /* log some info */ @@ -129,6 +129,6 @@ int CASIO_EXPORT casio_decode_mcs_spreadsheet(casio_mcsfile_t **h, /* end */ err = 0; fail: - free(cells); + casio_free(cells); return (err); } diff --git a/src/mcsfile/decode/mcs/string.c b/src/mcsfile/decode/mcs/string.c index b8372d6..9c23722 100644 --- a/src/mcsfile/decode/mcs/string.c +++ b/src/mcsfile/decode/mcs/string.c @@ -36,7 +36,7 @@ int CASIO_EXPORT casio_decode_mcs_string(casio_mcsfile_t **h, /* print content */ msg((ll_info, "String MCS file is not managed yet. Content:")); - str = malloc(length); + str = casio_alloc(length, 1); if (!str) { err = casio_error_alloc; goto fail; } GREAD(str, length) mem((ll_info, str, length)); @@ -48,6 +48,6 @@ int CASIO_EXPORT casio_decode_mcs_string(casio_mcsfile_t **h, /* end */ err = 0; fail: - free(str); + casio_free(str); return (err); } diff --git a/src/mcsfile/duplicate.c b/src/mcsfile/duplicate.c index 5afa517..ed3bfe0 100644 --- a/src/mcsfile/duplicate.c +++ b/src/mcsfile/duplicate.c @@ -33,12 +33,12 @@ int CASIO_EXPORT casio_duplicate_mcsfile(casio_mcsfile_t **h, int err; casio_mcsfile_t *handle = NULL; /* Make the handle. */ - *h = malloc(sizeof(casio_mcsfile_t)); handle = *h; + *h = casio_alloc(1, sizeof(casio_mcsfile_t)); handle = *h; if (!handle) return (casio_error_alloc); /* Copy the file. */ err = casio_copy_mcsfile(handle, orig); - if (err) { free(handle); return (err); } + if (err) { casio_free(handle); return (err); } /* Set the 'alloc' flag and return. */ handle->casio_mcsfile_head.casio_mcshead_flags |= casio_mcsflag_alloc; diff --git a/src/mcsfile/free.c b/src/mcsfile/free.c index 13f843a..1047ac9 100644 --- a/src/mcsfile/free.c +++ b/src/mcsfile/free.c @@ -34,27 +34,27 @@ void CASIO_EXPORT casio_free_mcsfile(casio_mcsfile_t *handle) switch (handle->casio_mcsfile_head.casio_mcshead_type) { /* free the cells */ - case casio_mcstype_mat: case casio_mcstype_vct: + case casio_mcstype_mat: case casio_mcstype_vct: case casio_mcstype_list: case casio_mcstype_ssheet: if (handle->casio_mcsfile_head.casio_mcshead_width && handle->casio_mcsfile_head.casio_mcshead_height) { - free(handle->casio_mcsfile_cells[0]); - free(handle->casio_mcsfile_cells); + casio_free(handle->casio_mcsfile_cells[0]); + casio_free(handle->casio_mcsfile_cells); } break; /* free the set of pixels */ case casio_mcstype_pict: case casio_mcstype_capt: for (i = 0; i < handle->casio_mcsfile_head.casio_mcshead_count; i++) - free(handle->casio_mcsfile_pics[i]); + casio_free(handle->casio_mcsfile_pics[i]); if (handle->casio_mcsfile_pics != &handle->casio_mcsfile_pic) - free(handle->casio_mcsfile_pics); + casio_free(handle->casio_mcsfile_pics); break; /* free the variables */ case casio_mcstype_alphamem: if (handle->casio_mcsfile_vars != &handle->casio_mcsfile_var) - free(handle->casio_mcsfile_vars); + casio_free(handle->casio_mcsfile_vars); break; /* free nothing */ @@ -65,11 +65,11 @@ void CASIO_EXPORT casio_free_mcsfile(casio_mcsfile_t *handle) /* free the raw content */ default: - free(handle->casio_mcsfile_content); + casio_free(handle->casio_mcsfile_content); } /* free the content */ - if (handle->casio_mcsfile_head.casio_mcshead_flags & casio_mcsflag_alloc) - free(handle); handle->casio_mcsfile_head.casio_mcshead_flags &= ~casio_mcsflag_valid; + if (handle->casio_mcsfile_head.casio_mcshead_flags & casio_mcsflag_alloc) + casio_free(handle); } diff --git a/src/mcsfile/head.c b/src/mcsfile/head.c new file mode 100644 index 0000000..f75c857 --- /dev/null +++ b/src/mcsfile/head.c @@ -0,0 +1,85 @@ +/* **************************************************************************** + * mcsfile/head.c -- correct a main memory head. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "mcsfile.h" +#include "reference/reference.h" + +/** + * casio_correct_mcshead: + * Correct the information. + * + * @arg head the MCS head to correct. + * @arg mcsfor the destination platform. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_correct_mcshead(casio_mcshead_t *head, + unsigned long mcsfor) +{ + int err; unsigned long inifor; + + /* Prepare. */ + inifor = head->casio_mcshead_flags & casio_mcsfor_mask; + mcsfor = mcsfor & casio_mcsfor_mask; + msg((ll_info, "Converting head from info type 0x%02X to 0x%02X", + inifor >> 24, mcsfor >> 24)); + + /* Check if has already been converted. */ + if (inifor == mcsfor) return (0); + + /* If we ought to convert from any specific type, + * we have to convert to abstract first. */ + switch (inifor) { + case 0: err = 0; break; + case casio_mcsfor_mcs: + err = casio_correct_mcshead_from_mcs(head); break; + case casio_mcsfor_cas40: /* FALLTHRU */ + case casio_mcsfor_cas50: + err = casio_correct_mcshead_from_casdata(head); break; +#if 0 /* TODO */ + case casio_mcsfor_cas100: + err = casio_correct_mcshead_from_cas100(head); break; +#endif + default: err = casio_error_op; + } + + /* If we have encountered an error while doing that, + * we should tell the user about it. */ + if (err) return (err); + head->casio_mcshead_flags &= ~casio_mcsfor_mask; + + /* Then we can convert from abstract to specific. */ + switch (mcsfor) { + case 0: return (0); + + case casio_mcsfor_mcs: + err = casio_correct_mcshead_to_mcs(head); break; + case casio_mcsfor_cas40: /* FALLTHRU */ + case casio_mcsfor_cas50: + err = casio_correct_mcshead_to_casdata(head); break; +#if 0 /* TODO */ + case casio_mcsfor_cas100: + err = casio_correct_mcshead_to_cas100(head); break; +#endif + default: err = casio_error_op; + } + + if (err) return (err); + head->casio_mcshead_flags |= mcsfor; + return (err); +} diff --git a/src/mcsfile/make.c b/src/mcsfile/make.c index 6c915d9..dc33f45 100644 --- a/src/mcsfile/make.c +++ b/src/mcsfile/make.c @@ -33,13 +33,13 @@ int CASIO_EXPORT casio_make_mcsfile(casio_mcsfile_t **h, int err; casio_mcsfile_t *handle; /* Allocate the handle. */ - *h = malloc(sizeof(casio_mcsfile_t)); handle = *h; + *h = casio_alloc(1, sizeof(casio_mcsfile_t)); handle = *h; if (!handle) return (casio_error_alloc); handle->casio_mcsfile_head.casio_mcshead_flags = 0; /* & ~mcsflag_valid */ /* Prepare it. */ err = casio_prepare_mcsfile(handle, rawhead); - if (err) { free(handle); return (err); } + if (err) { casio_free(handle); return (err); } /* Add the flag and return. */ handle->casio_mcsfile_head.casio_mcshead_flags |= casio_mcsflag_alloc; diff --git a/src/mcsfile/mcsfile.h b/src/mcsfile/mcsfile.h index 04975e0..a387d55 100644 --- a/src/mcsfile/mcsfile.h +++ b/src/mcsfile/mcsfile.h @@ -57,7 +57,8 @@ /* Picture utilities */ /* ************************************************************************* */ # define alloc_pixels(W, H) \ - malloc(sizeof(casio_pixel_t*) * (H) + sizeof(casio_pixel_t) * (W) * (H)) + casio_alloc(sizeof(casio_pixel_t*) \ + * (H) + sizeof(casio_pixel_t) * (W) * (H), 1) # define prepare_pixels(I, W, H) { \ unsigned int PIXPREP_y; \ casio_pixel_t *PIXPREP_line = (casio_pixel_t*)&(I)[(H)]; \ @@ -65,20 +66,5 @@ (I)[PIXPREP_y] = PIXPREP_line; \ PIXPREP_line += (W); \ }} -/* ************************************************************************* */ -/* Correspondances */ -/* ************************************************************************* */ -/* CAS app */ -extern int casio_maketype_casapp OF((casio_mcshead_t *casio__head, - int casio__ext, const char *casio__app)); - -/* CAS data type */ -extern int casio_maketype_cas OF((casio_mcshead_t *casio__head, - const char *casio__datatype)); - -/* MCS file */ -extern int casio_maketype_mcs OF((casio_mcshead_t *casio__head, - const char *casio__gname, const char *casio__dname, - const char *casio__fname, unsigned int casio__rawtype)); #endif diff --git a/src/mcsfile/prepare.c b/src/mcsfile/prepare.c index b01df18..6c35b0b 100644 --- a/src/mcsfile/prepare.c +++ b/src/mcsfile/prepare.c @@ -60,12 +60,12 @@ int CASIO_EXPORT casio_prepare_mcsfile(casio_mcsfile_t *handle, if (wd && ht) { handle->casio_mcsfile_cells = - malloc(sizeof(casio_mcscell_t*) * ht); + casio_alloc(ht, sizeof(casio_mcscell_t*)); if (!handle->casio_mcsfile_cells) goto fail; handle->casio_mcsfile_cells[0] = - malloc(sizeof(casio_mcscell_t) * wd * ht); + casio_alloc(wd * ht, sizeof(casio_mcscell_t)); if (!handle->casio_mcsfile_cells[0]) { - free(handle->casio_mcsfile_cells); goto fail; } + casio_free(handle->casio_mcsfile_cells); goto fail; } for (y = 1; y < ht; y++) handle->casio_mcsfile_cells[y] = &handle->casio_mcsfile_cells @@ -78,8 +78,8 @@ int CASIO_EXPORT casio_prepare_mcsfile(casio_mcsfile_t *handle, if (head->casio_mcshead_count <= 1) handle->casio_mcsfile_vars = &handle->casio_mcsfile_var; else { - handle->casio_mcsfile_vars = malloc(sizeof(casio_mcscell_t) - * head->casio_mcshead_count); + handle->casio_mcsfile_vars = casio_alloc(head->casio_mcshead_count, + sizeof(casio_mcscell_t)); if (!handle->casio_mcsfile_vars) goto fail; memset(handle->casio_mcsfile_vars, 0, sizeof(casio_mcscell_t) * head->casio_mcshead_count); @@ -89,15 +89,16 @@ int CASIO_EXPORT casio_prepare_mcsfile(casio_mcsfile_t *handle, /* allocate the set of pixels */ case casio_mcstype_pict: case casio_mcstype_capt: /* set count */ - head->casio_mcshead_count = - (head->casio_mcshead_type == casio_mcstype_pict) ? 2 : 1; + head->casio_mcshead_count = 1; + if (head->casio_mcshead_type == casio_mcstype_pict) + head->casio_mcshead_count = 2; /* allocate directory */ if (head->casio_mcshead_count <= 1) handle->casio_mcsfile_pics = &handle->casio_mcsfile_pic; else { - handle->casio_mcsfile_pics = malloc(sizeof(casio_pixel_t**) - * head->casio_mcshead_count); + handle->casio_mcsfile_pics = casio_alloc(head->casio_mcshead_count, + sizeof(casio_pixel_t**)); if (!handle->casio_mcsfile_pics) goto fail; } @@ -107,9 +108,9 @@ int CASIO_EXPORT casio_prepare_mcsfile(casio_mcsfile_t *handle, head->casio_mcshead_width, head->casio_mcshead_height); if (!handle->casio_mcsfile_pics[i]) { for (j = 0; j < i; j++) - free(handle->casio_mcsfile_pics[j]); + casio_free(handle->casio_mcsfile_pics[j]); if (handle->casio_mcsfile_pics != &handle->casio_mcsfile_pic) - free(handle->casio_mcsfile_pics); + casio_free(handle->casio_mcsfile_pics); goto fail; } } @@ -128,7 +129,8 @@ int CASIO_EXPORT casio_prepare_mcsfile(casio_mcsfile_t *handle, /* allocate raw content */ default: - handle->casio_mcsfile_content = malloc(head->casio_mcshead_size); + handle->casio_mcsfile_content = + casio_alloc(head->casio_mcshead_size, 1); if (!handle->casio_mcsfile_content) goto fail; break; } diff --git a/src/mcsfile/corresp/cas_app.c b/src/mcsfile/reference/cas_app.c similarity index 87% rename from src/mcsfile/corresp/cas_app.c rename to src/mcsfile/reference/cas_app.c index 518c5ad..ff12271 100644 --- a/src/mcsfile/corresp/cas_app.c +++ b/src/mcsfile/reference/cas_app.c @@ -1,5 +1,5 @@ /* **************************************************************************** - * mcsfile/corresp/cas_app.c -- get the CAS app out of raw identification data. + * mcsfile/reference/cas_app.c -- get the CAS app out of raw data. * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey * * 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 . * ************************************************************************* */ -#include "../mcsfile.h" +#include "reference.h" /* ************************************************************************* */ /* Local types */ @@ -86,17 +86,15 @@ CASIO_LOCAL const struct ext_corresp apps[] = { /* Main functions */ /* ************************************************************************* */ /** - * casio_maketype_casapp: + * casio_check_cas_app: * Get the CAS application from raw CASDYN identification data. * - * @arg head the head to fill. * @arg ext the extension value. * @arg app the application name. * @return the error (if any). */ -int CASIO_EXPORT casio_maketype_casapp(casio_mcshead_t *head, - int ext, const char *app) +int CASIO_EXPORT casio_check_cas_app(int ext, const char *app) { const struct ext_corresp *e; const struct app_corresp *a; @@ -114,19 +112,11 @@ int CASIO_EXPORT casio_maketype_casapp(casio_mcshead_t *head, break; } if (!a->name) goto notfound; - /* copy raw information */ - memset(head, 0, sizeof(casio_mcshead_t)); - head->casio_mcshead_flags |= e->info; /* FIXME */ - msg((ll_info, "Head info is 0x%04X", e->info)); - strncpy((char*)head->casio_mcshead_appname, app, 3); - head->casio_mcshead_appname[3] = 0; - - /* fill in info and return */ + /* return */ return (0); notfound: msg((ll_error, "Type with 0x%02X extension and '%.3s' app name was not " "implemented or recognized", ext, app)); - head->casio_mcshead_type = 0; return (1); } diff --git a/src/mcsfile/corresp/cas_data.c b/src/mcsfile/reference/cas_data.c similarity index 92% rename from src/mcsfile/corresp/cas_data.c rename to src/mcsfile/reference/cas_data.c index 22662a4..c65f63a 100644 --- a/src/mcsfile/corresp/cas_data.c +++ b/src/mcsfile/reference/cas_data.c @@ -1,5 +1,5 @@ /* **************************************************************************** - * mcsfile/corresp/cas_data.c -- get the CAS type out of raw id. data. + * mcsfile/reference/cas_data.c -- get the CAS type out of raw data. * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey * * 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 . * ************************************************************************* */ -#include "../mcsfile.h" +#include "reference.h" /* ************************************************************************* */ /* Local types */ @@ -37,7 +37,6 @@ struct type_corresp { casio_mcstype_t type; casio_pictureformat_t picformat; }; - /* ************************************************************************* */ /* Correspondances */ /* ************************************************************************* */ @@ -124,18 +123,17 @@ CASIO_LOCAL int get_number(const char *s, int *num) } /** - * casio_maketype_cas: - * Get the libcasio MCS type from the raw CAS40/CAS50 data type. + * casio_correct_mcshead_from_casdata: + * Get the abstract type from the CAS data type. * - * @arg head the head to fill. - * @arg datatype the data type string (2 bytes long). + * @arg head the head. * @return the error (if any). */ -int CASIO_EXPORT casio_maketype_cas(casio_mcshead_t *head, - const char *datatype) +int CASIO_EXPORT casio_correct_mcshead_from_casdata(casio_mcshead_t *head) { const struct type_corresp *c; + const char *datatype = head->casio_mcshead_datatype; int id = 0; /* copy information */ @@ -167,18 +165,18 @@ notfound: msg((ll_info, "Type with '%.2s' data string was not implemented or not " "recognized.", datatype)); head->casio_mcshead_type = 0; - return (1); + return (casio_error_op); } /** - * casio_correct_casfile_head: + * casio_correct_mcshead_to_cas: * Correct a CAS file head. * * @arg head the head to correct. * @return the error (0 if ok). */ -int CASIO_EXPORT casio_correct_casfile_head(casio_mcshead_t *head) +int CASIO_EXPORT casio_correct_mcshead_to_casdata(casio_mcshead_t *head) { const struct type_corresp *c; diff --git a/src/mcsfile/corresp/mcs.c b/src/mcsfile/reference/mcs.c similarity index 91% rename from src/mcsfile/corresp/mcs.c rename to src/mcsfile/reference/mcs.c index b41c159..1f125fb 100644 --- a/src/mcsfile/corresp/mcs.c +++ b/src/mcsfile/reference/mcs.c @@ -1,5 +1,5 @@ /* **************************************************************************** - * type/mcs.c -- get the MCS type out of raw identification data. + * mcsfile/reference/mcs.c -- get the MCS type out of raw data. * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey * * 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 . * ************************************************************************* */ -#include "../mcsfile.h" +#include "reference.h" /* ************************************************************************* */ /* Local types */ @@ -259,7 +259,6 @@ CASIO_LOCAL const struct group_corresp mcs_groups[] = { /* terminating entry */ {NULL, 0, NULL} }; - /* ************************************************************************* */ /* Main functions */ /* ************************************************************************* */ @@ -282,7 +281,8 @@ CASIO_LOCAL int get_number(const char *s, int *num, int isnum) else if (!strcmp(s, "\xCD")) *num = casio_r; else if (isnum) { - if (!(*num = atoi(s))) return (1); + if (!(*num = atoi(s))) + return (1); } else { if (*s < 'A' || *s > 'Z') return (1); @@ -292,22 +292,19 @@ CASIO_LOCAL int get_number(const char *s, int *num, int isnum) } /** - * casio_maketype_mcs: - * Get libcasio type from rawtype. + * casio_correct_mcshead_from_mcs: + * Make libcasio abstract data from raw MCS identification data. * - * @arg head the head to fill. - * @arg gname the group name. - * @arg dname the directory name. - * @arg fname the filename. - * @arg rawtype the raw numerical type. - * @return if the type was not found (0 if yes). + * @arg head the head to correct. + * @return if an error occured. */ -int CASIO_EXPORT casio_maketype_mcs(casio_mcshead_t *head, - const char *gname, const char *dname, - const char *fname, unsigned int rawtype) +int CASIO_EXPORT casio_correct_mcshead_from_mcs(casio_mcshead_t *head) { int gid = 0, fid = 0; + const char *gname = head->casio_mcshead_group; + const char *fname = head->casio_mcshead_name; + unsigned int rawtype = head->casio_mcshead_rawtype; const struct group_corresp *g; const struct type_corresp *t; @@ -315,20 +312,6 @@ int CASIO_EXPORT casio_maketype_mcs(casio_mcshead_t *head, msg((ll_info, "Looking for type with '%.8s' group, '%.8s' name and " "0x%02X raw type", gname, fname, rawtype)); - /* copy raw information */ - memset(head, 0, sizeof(casio_mcshead_t)); - head->casio_mcshead_flags |= casio_mcsfor_mcs; - memcpy(head->casio_mcshead_name, fname, 8); - head->casio_mcshead_name[8] = 0; - memcpy(head->casio_mcshead_group, gname, 16); - head->casio_mcshead_group[16] = 0; - head->casio_mcshead_rawtype = rawtype; - if (dname) { - memcpy(head->casio_mcshead_dirname, dname, 8); - head->casio_mcshead_dirname[8] = 0; - } else - memset(head->casio_mcshead_dirname, 0, 9); - /* look for group correspondance */ for (g = mcs_groups; g->types; g++) { size_t pl = strlen(g->name); @@ -381,14 +364,14 @@ notfound: } /** - * casio_correct_mcsfile_head: - * Correct information. + * casio_correct_mcshead_to_mcs: + * Make MCS raw data from the abstract data. * - * @arg head the mcs head to correct. + * @arg head the MCS head to correct. * @return if an error was encountered. */ -int CASIO_EXPORT casio_correct_mcsfile_head(casio_mcshead_t *head) +int CASIO_EXPORT casio_correct_mcshead_to_mcs(casio_mcshead_t *head) { const struct group_corresp *g; const struct type_corresp *t; @@ -406,18 +389,15 @@ int CASIO_EXPORT casio_correct_mcsfile_head(casio_mcshead_t *head) if (t->type != head->casio_mcshead_type) continue; /* check if id is weighted by major */ - if (casio_get_id_major(head->casio_mcshead_id)) { - if (~t->flags & weight_by_gid) - continue; - } else - continue; + if (casio_get_id_major(head->casio_mcshead_id) + && ~t->flags & weight_by_gid) continue; /* we have found the entry! */ goto found; } /* not found... */ - return (casio_error_unknown); + return (casio_error_op); found: /* put the group name */ @@ -461,10 +441,12 @@ found: } else if (t->name) strcpy(nm, t->name); + /* put the raw type */ + head->casio_mcshead_rawtype = t->rawtype; + /* no error */ return (0); } - /* ************************************************************************* */ /* Compare function */ /* ************************************************************************* */ diff --git a/src/mcsfile/reference/reference.h b/src/mcsfile/reference/reference.h new file mode 100644 index 0000000..6315e2b --- /dev/null +++ b/src/mcsfile/reference/reference.h @@ -0,0 +1,42 @@ +/* **************************************************************************** + * mcsfile/reference/reference.h -- reference functions. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#ifndef LOCAL_MCSFILE_REFERENCE_H +# define LOCAL_MCSFILE_REFERENCE_H 1 +# include "../mcsfile.h" + +/* MCS metadata. */ + +CASIO_EXTERN int CASIO_EXPORT casio_correct_mcshead_from_mcs + OF((casio_mcshead_t *casio__head)); +CASIO_EXTERN int CASIO_EXPORT casio_correct_mcshead_to_mcs + OF((casio_mcshead_t *casio__head)); + +/* CAS40 & CAS50 data type. */ + +CASIO_EXTERN int CASIO_EXPORT casio_correct_mcshead_from_casdata + OF((casio_mcshead_t *casio__head)); +CASIO_EXTERN int CASIO_EXPORT casio_correct_mcshead_to_casdata + OF((casio_mcshead_t *casio__head)); + +/* Check if a CAS app exists. */ + +CASIO_EXTERN int CASIO_EXPORT casio_check_cas_app + OF((int casio__ext, const char *casio__app)); + +#endif /* LOCAL_MCSFILE_REFERENCE_H */ diff --git a/src/stream/builtin/file.c b/src/stream/builtin/file.c index f4613d7..02a0e1d 100644 --- a/src/stream/builtin/file.c +++ b/src/stream/builtin/file.c @@ -196,7 +196,7 @@ CASIO_LOCAL int casio_file_close(file_cookie_t *cookie) if (cookie->_wstream && cookie->_wstream != cookie->_rstream && cookie->_wstream_cl) fclose(cookie->_wstream); - free(cookie); + casio_free(cookie); return (0); } /* ************************************************************************* */ @@ -234,7 +234,7 @@ int CASIO_EXPORT casio_open_stream_file(casio_stream_t **stream, } /* allocate the cookie */ - cookie = malloc(sizeof(file_cookie_t)); + cookie = casio_alloc(1, sizeof(file_cookie_t)); if (!cookie) { err = casio_error_alloc; goto fail; } /* fill the cookie */ diff --git a/src/stream/builtin/libusb.c b/src/stream/builtin/libusb.c index 3491268..8f8364d 100644 --- a/src/stream/builtin/libusb.c +++ b/src/stream/builtin/libusb.c @@ -71,7 +71,7 @@ CASIO_LOCAL int casio_libusb_close(void *vcookie) if (cookie->_handle) libusb_close(cookie->_handle); if (cookie->_context) libusb_exit(cookie->_context); - free(vcookie); + casio_free(vcookie); return (0); } /* ************************************************************************* */ @@ -330,7 +330,7 @@ int CASIO_EXPORT casio_openusb_libusb(casio_stream_t **stream) } /* make the cookie */ - cookie = malloc(sizeof(libusb_cookie_t)); + cookie = casio_alloc(1, sizeof(libusb_cookie_t)); err = casio_error_alloc; if (!cookie) goto fail; cookie->_context = context; @@ -342,7 +342,7 @@ int CASIO_EXPORT casio_openusb_libusb(casio_stream_t **stream) return (casio_open(stream, CASIO_OPENMODE_READ | CASIO_OPENMODE_WRITE, casio_streamtype_usb, cookie, &casio_libusb_callbacks)); fail: - if (cookie) free(cookie); + if (cookie) casio_free(cookie); if (dhandle) libusb_close(dhandle); if (context) libusb_exit(context); return (err); diff --git a/src/stream/builtin/limited.c b/src/stream/builtin/limited.c index 5ecf7f9..89ee6cf 100644 --- a/src/stream/builtin/limited.c +++ b/src/stream/builtin/limited.c @@ -65,7 +65,7 @@ CASIO_LOCAL int casio_limited_read(void *vcookie, unsigned char *dest, size_t si CASIO_LOCAL int casio_limited_close(void *vcookie) { - free(vcookie); + casio_free(vcookie); return (0); } @@ -93,7 +93,7 @@ int CASIO_EXPORT casio_open_limited(casio_stream_t **stream, /* FIXME: check original stream */ /* allocate the cookie */ - cookie = malloc(sizeof(limited_cookie_t)); + cookie = casio_alloc(1, sizeof(limited_cookie_t)); if (!cookie) return (casio_error_alloc); /* fill the cookie */ diff --git a/src/stream/builtin/memory.c b/src/stream/builtin/memory.c index 0eb971a..c68007a 100644 --- a/src/stream/builtin/memory.c +++ b/src/stream/builtin/memory.c @@ -123,7 +123,7 @@ CASIO_LOCAL int casio_memory_seek(void *vcookie, casio_off_t *offset, CASIO_LOCAL int casio_memory_close(void *vcookie) { - free(vcookie); + casio_free(vcookie); return (0); } @@ -154,7 +154,7 @@ int CASIO_EXPORT casio_open_memory(casio_stream_t **stream, return (casio_error_nostream); /* allocate the cookie */ - cookie = malloc(sizeof(memory_cookie_t)); + cookie = casio_alloc(1, sizeof(memory_cookie_t)); if (!cookie) return (casio_error_alloc); /* fill the cookie */ diff --git a/src/stream/builtin/streams.c b/src/stream/builtin/streams.c index aafce40..7cc9de1 100644 --- a/src/stream/builtin/streams.c +++ b/src/stream/builtin/streams.c @@ -219,7 +219,7 @@ CASIO_LOCAL int casio_streams_close(void *vcookie) close(cookie->_writefd); /* free the cookie. */ - free(cookie); + casio_free(cookie); return (0); } /* ************************************************************************* */ @@ -489,7 +489,7 @@ int CASIO_EXPORT casio_open_stream_fd(casio_stream_t **stream, if (!mode) { err = casio_error_invalid; goto fail; } /* allocate cookie */ - cookie = malloc(sizeof(streams_cookie_t)); + cookie = casio_alloc(1, sizeof(streams_cookie_t)); if (!cookie) { err = casio_error_alloc; goto fail; } cookie->_readfd = readfd; cookie->_writefd = writefd; diff --git a/src/stream/builtin/windows.c b/src/stream/builtin/windows.c index bd1ee3a..ad4d346 100644 --- a/src/stream/builtin/windows.c +++ b/src/stream/builtin/windows.c @@ -90,7 +90,7 @@ CASIO_LOCAL char *wfind(unsigned int vid, unsigned int pid) msg((ll_info, "Allocating space for interface information detail (%luo)", RequiredSize)); - DeviceInterfaceDetailData = malloc(RequiredSize); + DeviceInterfaceDetailData = casio_alloc(RequiredSize, 1); if (!DeviceInterfaceDetailData) { msg((ll_error, "Memory allocation failed. Oh well.")); break ; @@ -113,13 +113,13 @@ CASIO_LOCAL char *wfind(unsigned int vid, unsigned int pid) Path = DeviceInterfaceDetailData->DevicePath; msg((ll_info, "Stumbled across: %s", Path)); if (strstr(Path, vidpid)) { - devpath = malloc(strlen(Path) + 1); + devpath = casio_alloc(strlen(Path) + 1, 1); if (!devpath) break; strcpy(devpath, Path); } /* free the allocated detail */ - free(DeviceInterfaceDetailData); + casio_free(DeviceInterfaceDetailData); if (devpath) break ; } @@ -272,7 +272,7 @@ CASIO_LOCAL int casio_win_close(void *vcookie) { win_cookie_t *cookie = (win_cookie_t*)vcookie; CloseHandle(cookie->_handle); - free(cookie); + casio_free(cookie); return (0); } /* ************************************************************************* */ @@ -354,9 +354,9 @@ CASIO_LOCAL int casio_win_seek(void *vcookie, casio_off_t *offset, /* get the move method */ DWORD MoveMethod; switch (whence) { - case CASIO_SEEK_CUR: MoveMethod = FILE_CURRENT; - case CASIO_SEEK_END: MoveMethod = FILE_END; - default /* CASIO_SEEK_SET */: MoveMethod = FILE_BEGIN; } + case CASIO_SEEK_CUR: MoveMethod = FILE_CURRENT; break; + case CASIO_SEEK_END: MoveMethod = FILE_END; break; + default /* CASIO_SEEK_SET */: MoveMethod = FILE_BEGIN; break; } ret = SetFilePointer(cookie->_handle, (LONG)*offset, NULL, MoveMethod); if (ret == INVALID_SET_FILE_POINTER) @@ -435,8 +435,8 @@ int CASIO_EXPORT casio_openusb_windows(casio_stream_t **stream) p = wfind(0x07cf, 0x6101); if (!p) return (casio_error_nocalc); - err = casio_open_stream_windows(stream, path); - free(p); + err = casio_opencom_windows(stream, p); + casio_free(p); return (err); } @@ -473,7 +473,7 @@ int CASIO_EXPORT casio_opencom_windows(casio_stream_t **stream, /* make cookie */ msg((ll_info, "Making the cookie")); - cookie = malloc(sizeof(win_cookie_t)); + cookie = casio_alloc(1, sizeof(win_cookie_t)); err = casio_error_alloc; if (!cookie) goto fail; @@ -483,11 +483,11 @@ int CASIO_EXPORT casio_opencom_windows(casio_stream_t **stream, cookie->_end = 1; /* initialize for real */ - return (casio_open(stream, CASIO_MODE_READ | CASIO_MODE_WRITE, + return (casio_open(stream, CASIO_OPENMODE_READ | CASIO_OPENMODE_WRITE, casio_streamtype_serial, cookie, &casio_windows_callbacks)); fail: if (fhandle != INVALID_HANDLE_VALUE) CloseHandle(fhandle); - if (cookie) free(cookie); + if (cookie) casio_free(cookie); return (err); } diff --git a/src/stream/open.c b/src/stream/open.c index d83bd7a..d13449c 100644 --- a/src/stream/open.c +++ b/src/stream/open.c @@ -40,7 +40,7 @@ int CASIO_EXPORT casio_open(casio_stream_t **pstream, casio_openmode_t mode, casio_streamfuncs_t *c; /* allocate the stream */ - *pstream = malloc(sizeof(casio_stream_t)); + *pstream = casio_alloc(1, sizeof(casio_stream_t)); stream = *pstream; checknot(stream == NULL, casio_error_alloc) @@ -73,7 +73,7 @@ int CASIO_EXPORT casio_open(casio_stream_t **pstream, casio_openmode_t mode, err = 0; fail: if (err) { - free(stream); + casio_free(stream); (*callbacks->casio_streamfuncs_close)(cookie); } return (err); @@ -94,6 +94,6 @@ int CASIO_EXPORT casio_close(casio_stream_t *stream) if (!stream) return (0); c = getcb(stream, close); if (c) (*c)(stream->casio_stream_cookie); - free(stream); + casio_free(stream); return (0); } diff --git a/src/stream/read.c b/src/stream/read.c index c752d7e..42b5fd6 100644 --- a/src/stream/read.c +++ b/src/stream/read.c @@ -38,7 +38,10 @@ int CASIO_EXPORT casio_read(casio_stream_t *stream, void *dest, size_t size) /* read */ if (!size) return (0); err = (*getcb(stream, read))(stream->casio_stream_cookie, dest, size); - failure(err, err) + if (err) { + msg((ll_error, "Stream reading failure: %s", casio_strerror(err))); + goto fail; + } /* move the cursor and return */ stream->casio_stream_offset += size; diff --git a/src/stream/write.c b/src/stream/write.c index 5deddf4..128a8ed 100644 --- a/src/stream/write.c +++ b/src/stream/write.c @@ -40,7 +40,10 @@ int CASIO_EXPORT casio_write(casio_stream_t *stream, /* write */ if (!size) return (0); err = (*getcb(stream, write))(stream->casio_stream_cookie, data, size); - failure(err, err) + if (err) { + msg((ll_error, "Stream writing failure: %s", casio_strerror(err))); + goto fail; + } /* move the cursor and return */ stream->casio_stream_offset += size; @@ -61,7 +64,7 @@ fail: int CASIO_EXPORT casio_write_char(casio_stream_t *stream, int car) { - char ccar = car; + unsigned char ccar = car; return (casio_write(stream, &ccar, 1)); } diff --git a/src/utils/alloc.c b/src/utils/alloc.c new file mode 100644 index 0000000..98b2cf7 --- /dev/null +++ b/src/utils/alloc.c @@ -0,0 +1,45 @@ +/* **************************************************************************** + * utils/alloc.c -- dynamic memory allocation utilities. + * Copyright (C) 2016-2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "../internals.h" + +/** + * casio_alloc: + * Allocate memory dynamically. + * + * @arg num the number of elements. + * @arg size the size of an element. + * @return the allocated memory region. + */ + +void* CASIO_EXPORT casio_alloc(size_t num, size_t size) +{ + return (malloc(num * size)); +} + +/** + * casio_free: + * Free dynamically allocated memory. + * + * @arg ptr the pointer to the allocated memory. + */ + +void CASIO_EXPORT casio_free(void *ptr) +{ + free(ptr); +} diff --git a/src/utils/mutex.c b/src/utils/mutex.c new file mode 100644 index 0000000..8b632fd --- /dev/null +++ b/src/utils/mutex.c @@ -0,0 +1,80 @@ +/* **************************************************************************** + * utils/mutex.c -- mutex internals. + * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey + * + * 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 . + * ************************************************************************* */ +#include "../internals.h" + +/** + * casio_init_mutex: + * Initialize a mutex. + * + * @arg mutex the mutex to initialize. + */ + +void CASIO_EXPORT casio_init_mutex(casio_mutex_t *mutex) +{ + *mutex = 0; +} + +/** + * casio_lock_mutex: + * Lock a mutex. + * + * @arg mutex the mutex to lock. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_lock_mutex(casio_mutex_t *mutex) +{ + int err; + + if (!*mutex) goto unlocked; + if ((err = casio_sleep(0))) return (err); + while (*(volatile casio_mutex_t*)mutex) + casio_sleep(5); + +unlocked: + *mutex = 1; + return (0); +} + +/** + * casio_trylock_mutex: + * Try to lock a mutex. + * + * @arg mutex the mutex to lock. + * @return the error code (0 if ok). + */ + +int CASIO_EXPORT casio_trylock_mutex(casio_mutex_t *mutex) +{ + if (*mutex) return (casio_error_lock); + *mutex = 1; + return (0); +} + +/** + * casio_unlock_mutex: + * Unlock a mutex. + * + * @arg mutex the mutex to unlock. + */ + +void CASIO_EXPORT casio_unlock_mutex(casio_mutex_t *mutex) +{ + *mutex = 0; +}