1. Use lib/libm for small (non-Express builds) to gain back a lot of flash space.

2. Add flag INTERNAL_LIBM to mpconfigboard.mk files to signal using lib/libm.
3. Fix floating-point warnings in lib/libm
4. Turn off -finline-limit, no longer needed due to 1.
5. Add explicit flags for SPI_FLASH_FILESYSTEM and INTERNAL_FLASH_FILESYSTEM
to mpconfigboard.mk files, so they don't need to know the name of the .c file
that implements those. Makefile takes care of checking the flags and including
the right files.
This commit is contained in:
Dan Halbert 2017-10-15 14:02:42 -04:00 committed by Scott Shawcroft
parent 8f3be0a037
commit dbd3f15168
16 changed files with 82 additions and 18 deletions

View File

@ -135,11 +135,12 @@ ifeq ($(DEBUG), 1)
# -DMICROPY_DEBUG_MODULES may also be added to an -flto build, if you wish.
CFLAGS += -Os -ggdb -DNDEBUG -DENABLE_MICRO_TRACE_BUFFER -DMICROPY_DEBUG_MODULES
else
# GCC_INLINE_LIMIT specifies -finline-limit, which can shrink the image size.
# -finline-limit can shrink the image size.
# -finline-limit=80 or so is similar to not having it on.
# There is no simple default value, though.
ifeq ($(FLASH_IMPL),internal_flash.c)
GCC_INLINE_LIMIT = -finline-limit=19
ifdef INTERNAL_FLASH_FILESYSTEM
## Not currently needed
## CFLAGS += -finline-limit=50
endif
CFLAGS += -Os -DNDEBUG -flto $(GCC_INLINE_LIMIT)
endif
@ -161,10 +162,14 @@ CFLAGS += -DMICROPY_MODULE_FROZEN_MPY
CFLAGS += -Wno-error=lto-type-mismatch
endif
#LIBM_FILE_NAME = $(shell $(CC) $(CFLAGS) -print-file-name=libm.a)
LDFLAGS = $(CFLAGS) -nostartfiles -fshort-enums -mthumb -mcpu=cortex-m0plus -Lasf/thirdparty/CMSIS/Lib/GCC/ -Wl,-nostdlib -Wl,-T,$(LD_FILE) -Wl,-Map=$@.map -Wl,-cref -Wl,-gc-sections -specs=nano.specs
LIBS = -larm_cortexM0l_math -lm -lgcc -lc
# Use toolchain libm if we're not using our own.
ifndef INTERNAL_LIBM
LIBS += -lm
endif
SRC_ASF = $(addprefix asf/sam0/,\
drivers/adc/adc_sam_d_r/adc.c \
drivers/dac/dac_sam_d_c/dac.c \
@ -237,6 +242,16 @@ SRC_C = \
lib/libc/string0.c \
lib/mp-readline/readline.c
# Choose which flash filesystem impl to use.
# (Right now INTERNAL_FLASH_FILESYSTEM and SPI_FLASH_FILESYSTEM are mutually exclusive.
# But that might not be true in the future.)
ifdef INTERNAL_FLASH_FILESYSTEM
SRC_C += internal_flash.c
endif
ifdef SPI_FLASH_FILESYSTEM
SRC_C += spi_flash.c
endif
SRC_COMMON_HAL = \
analogio/__init__.c \
analogio/AnalogIn.c \
@ -270,6 +285,30 @@ SRC_COMMON_HAL = \
usb_hid/__init__.c \
usb_hid/Device.c
ifdef INTERNAL_LIBM
SRC_LIBM = $(addprefix lib/,\
libm/math.c \
libm/fmodf.c \
libm/nearbyintf.c \
libm/ef_sqrt.c \
libm/kf_rem_pio2.c \
libm/kf_sin.c \
libm/kf_cos.c \
libm/kf_tan.c \
libm/ef_rem_pio2.c \
libm/sf_sin.c \
libm/sf_cos.c \
libm/sf_tan.c \
libm/sf_frexp.c \
libm/sf_modf.c \
libm/sf_ldexp.c \
libm/asinfacosf.c \
libm/atanf.c \
libm/atan2f.c \
)
endif
# These don't have corresponding files in each port but are still located in
# shared-bindings to make it clear what the contents of the modules are.
SRC_BINDINGS_ENUMS = \
@ -304,6 +343,9 @@ OBJ = $(PY_O) $(addprefix $(BUILD)/, $(SRC_C:.c=.o))
OBJ += $(addprefix $(BUILD)/, $(SRC_ASF:.c=.o))
OBJ += $(addprefix $(BUILD)/, $(SRC_COMMON_HAL_EXPANDED:.c=.o))
OBJ += $(addprefix $(BUILD)/, $(SRC_SHARED_MODULE_EXPANDED:.c=.o))
ifdef INTERNAL_LIBM
OBJ += $(addprefix $(BUILD)/, $(SRC_LIBM:.c=.o))
endif
SRC_QSTR += $(SRC_C) $(SRC_COMMON_HAL_EXPANDED) $(SRC_SHARED_MODULE_EXPANDED) $(STM_SRC_C)

View File

@ -2,6 +2,7 @@ LD_FILE = boards/samd21x18-bootloader.ld
USB_VID = 0x2341
USB_PID = 0x824D
FLASH_IMPL = internal_flash.c
INTERNAL_FLASH_FILESYSTEM = 1
INTERNAL_LIBM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,7 +2,7 @@ LD_FILE = boards/samd21x18-bootloader-external-flash-crystalless.ld
USB_VID = 0x239A
USB_PID = 0x8019
FLASH_IMPL = spi_flash.c
SPI_FLASH_FILESYSTEM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,6 +2,7 @@ LD_FILE = boards/samd21x18-bootloader.ld
USB_VID = 0x239A
USB_PID = 0x8015
FLASH_IMPL = internal_flash.c
INTERNAL_FLASH_FILESYSTEM = 1
INTERNAL_LIBM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,7 +2,8 @@ LD_FILE = boards/samd21x18-bootloader.ld
USB_VID = 0x239A
USB_PID = 0x8015
FLASH_IMPL = internal_flash.c
INTERNAL_FLASH_FILESYSTEM = 1
INTERNAL_LIBM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,6 +2,6 @@ LD_FILE = boards/samd21x18-bootloader-external-flash.ld
USB_VID = 0x239A
USB_PID = 0x801b
FLASH_IMPL = spi_flash.c
SPI_FLASH_FILESYTEM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,6 +2,7 @@ LD_FILE = boards/samd21x18-bootloader.ld
USB_VID = 0x239A
USB_PID = 0x801D
FLASH_IMPL = internal_flash.c
INTERNAL_FLASH_FILESYSTEM = 1
INTERNAL_LIBM = 1
CHIP_VARIANT = SAMD21E18A

View File

@ -2,6 +2,6 @@ LD_FILE = boards/samd21x18-bootloader-external-flash.ld
USB_VID = 0x239A
USB_PID = 0x8014
FLASH_IMPL = spi_flash.c
SPI_FLASH_FILESYSTEM = 1
CHIP_VARIANT = SAMD21G18A

View File

@ -2,6 +2,7 @@ LD_FILE = boards/samd21x18-bootloader.ld
USB_VID = 0x239A
USB_PID = 0x801F
FLASH_IMPL = internal_flash.c
INTERNAL_FLASH_FILESYSTEM = 1
INTERNAL_LIBM = 1
CHIP_VARIANT = SAMD21E18A

View File

@ -2,7 +2,7 @@ LD_FILE = boards/samd21x18-bootloader-external-flash-crystalless.ld
USB_VID = 0x239A
USB_PID = 0x801F
FLASH_IMPL = spi_flash.c
SPI_FLASH_FILESYSTEM = 1
CHIP_VARIANT = SAMD21E18A
CHIP_FAMILY = samd21

View File

@ -189,6 +189,8 @@ extern const struct _mp_obj_module_t usb_hid_module;
#define MICROPY_PY_FRAMEBUF (0)
#define EXTRA_BUILTIN_MODULES
#define MICROPY_PY_BUILTINS_COMPLEX (0)
#define MICROPY_BUILTIN_METHOD_CHECK_SELF_ARG (0)
#define MICROPY_CPYTHON_COMPAT (0)
#endif

View File

@ -151,7 +151,7 @@ pio2_3t = 6.1232342629e-17; /* 0x248d3132 */
fn = (float)n;
r = t-fn*pio2_1;
w = fn*pio2_1t; /* 1st round good to 40 bit */
if(n<32&&(ix&0xffffff00)!=npio2_hw[n-1]) {
if(n<32&&(__int32_t)(ix&0xffffff00)!=npio2_hw[n-1]) {
y[0] = r-w; /* quick check no cancellation */
} else {
__uint32_t high;
@ -195,7 +195,10 @@ pio2_3t = 6.1232342629e-17; /* 0x248d3132 */
}
tx[2] = z;
nx = 3;
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wfloat-equal"
while(tx[nx-1]==zero) nx--; /* skip zero term */
#pragma GCC diagnostic pop
n = __kernel_rem_pio2f(tx,y,e0,nx,2,two_over_pi);
if(hx<0) {y[0] = -y[0]; y[1] = -y[1]; return -n;}
return n;

View File

@ -138,7 +138,10 @@ recompute:
}
/* check if recomputation is needed */
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wfloat-equal"
if(z==zero) {
#pragma GCC diagnostic pop
j = 0;
for (i=jz-1;i>=jk;i--) j |= iq[i];
if(j==0) { /* need recomputation */
@ -155,7 +158,10 @@ recompute:
}
/* chop off zero terms */
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wfloat-equal"
if(z==(float)0.0) {
#pragma GCC diagnostic pop
jz -= 1; q0 -= 8;
while(iq[jz]==0) { jz--; q0-=8;}
} else { /* break z into 8-bit if necessary */

View File

@ -338,7 +338,7 @@ float powf(float x, float y)
return sn*huge*huge; /* overflow */
} else if ((j&0x7fffffff) > 0x43160000) /* z < -150 */ // FIXME: check should be (uint32_t)j > 0xc3160000
return sn*tiny*tiny; /* underflow */
else if (j == 0xc3160000) { /* z == -150 */
else if (j == (int32_t) 0xc3160000) { /* z == -150 */
if (p_l <= z-p_h)
return sn*tiny*tiny; /* underflow */
}
@ -585,13 +585,13 @@ float expm1f(float x)
/*****************************************************************************/
/*****************************************************************************/
/* k is such that k*ln2 has minimal relative error and x - kln2 > log(FLT_MIN) */
static const int k = 235;
static const float kln2 = 0x1.45c778p+7f;
/* expf(x)/2 for x >= log(FLT_MAX), slightly better than 0.5f*expf(x/2)*expf(x/2) */
float __expo2f(float x)
{
/* k is such that k*ln2 has minimal relative error and x - kln2 > log(FLT_MIN) */
static const int k = 235;
static const float kln2 = 0x1.45c778p+7f;
float scale;
/* note that k is odd and scale*scale overflows */

View File

@ -15,7 +15,10 @@ float nearbyintf(float x)
y = x - 0x1p23f + 0x1p23f;
else
y = x + 0x1p23f - 0x1p23f;
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wfloat-equal"
if (y == 0)
#pragma GCC diagnostic pop
return s ? -0.0f : 0.0f;
return y;
}

View File

@ -32,7 +32,10 @@
float value; int exp;
#endif
{
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wfloat-equal"
if(!isfinite(value)||value==(float)0.0) return value;
#pragma GCC diagnostic pop
value = scalbnf(value,exp);
//if(!finitef(value)||value==(float)0.0) errno = ERANGE;
return value;