Commit 106ae09c authored by Dave Griffiths's avatar Dave Griffiths
Browse files

added configure build system

parent c0810fc5
TARGET := jellyfish
SRCS := src/main.cpp\
src/core/fixed.cpp\
src/core/list.cpp\
src/core/idmap.cpp\
src/scheme/scheme.cpp\
src/core/geometry.cpp\
src/core/noise.cpp\
src/fluxa/Sample.cpp\
src/fluxa/Allocator.cpp\
src/fluxa/Graph.cpp\
src/fluxa/GraphNode.cpp\
src/fluxa/Modules.cpp\
src/fluxa/ModuleNodes.cpp\
src/engine/obj_reader.cpp\
src/engine/engine.cpp\
src/engine/primitive.cpp\
src/engine/text_primitive.cpp\
src/engine/scenegraph.cpp\
src/engine/scenenode.cpp\
src/engine/texture.cpp\
src/engine/nomadic.cpp\
src/engine/jellyfish_primitive.cpp\
src/engine/jellyfish.cpp
# for the minute, go out and up to link to the vision lib
CCFLAGS = -ggdb -Wall -O3 -fpermissive -ffast-math -Wno-unused -DFLX_LINUX -Isrc -DASSETS_PATH=@prefix@/lib/jellyfish/
LDFLAGS =
LIBS = -lglut -lGL -lpng -lpthread -ldl -llo -ljpeg
CC = @CXX@
OBJS := ${SRCS:.cpp=.o}
DEPS := ${SRCS:.cpp=.dep}
XDEPS := $(wildcard ${DEPS})
.PHONY: all clean distclean
all:: ${TARGET}
ifneq (${XDEPS},)
include ${XDEPS}
endif
${TARGET}: ${OBJS} ${COBJS}
${CC} ${LDFLAGS} -o $@ $^ ${LIBS}
${OBJS}: %.o: %.cpp %.dep
${CC} ${CCFLAGS} -o $@ -c $<
${DEPS}: %.dep: %.cpp Makefile
${CC} ${CCFLAGS} -MM $< > $@
clean::
-rm -f *~ src/*.o ${TARGET}
cleandeps:: clean
-rm -f src/*.dep
install:: ${TARGET}
-cp jellyfish @prefix@/bin/
mkdir @prefix@/lib/jellyfish/
-cp assets @prefix@/lib/jellyfish/ -r
distclean:: clean
#include <jni.h>
#include <sys/time.h>
#include <time.h>
#include <android/log.h>
#include <stdint.h>
#include <stdio.h>
#include "scheme/scheme.h"
static int sWindowWidth = 320;
static int sWindowHeight = 480;
void Java_foam_starwisp_Scheme_nativeInit(JNIEnv* env)
{
appInit();
}
/* Call to initialize the graphics state */
void Java_foam_starwisp_Scheme_nativeInitGL( JNIEnv* env )
{
importGLInit();
initGL();
}
void Java_foam_starwisp_Scheme_nativeResize( JNIEnv* env, jobject thiz, jint w, jint h )
{
sWindowWidth = w;
sWindowHeight = h;
__android_log_print(ANDROID_LOG_INFO, "SanAngeles", "resize w=%d h=%d", w, h);
}
void Java_foam_starwisp_Scheme_nativeDone(JNIEnv* env)
{
appDeinit();
importGLDeinit();
}
void Java_foam_starwisp_Scheme_nativeRender( JNIEnv* env )
{
appRender(sWindowWidth, sWindowHeight);
}
jstring Java_foam_starwisp_Scheme_nativeEval(JNIEnv* env, jobject thiz, jstring code)
{
const char *native_code = (*env)->GetStringUTFChars(env, code, 0);
appEval(native_code);
(*env)->ReleaseStringUTFChars(env, code, native_code);
if (starwisp_data!=NULL) {
jstring ret = (*env)->NewStringUTF(env,starwisp_data);
free(starwisp_data);
starwisp_data=NULL;
return ret;
}
return (*env)->NewStringUTF(env,"");
}
void Java_foam_starwisp_Scheme_nativeLoadTexture(JNIEnv* env, jobject thiz, jstring texname, jbyteArray arr, jint w, jint h)
{
char *data = (char *) (*env)->GetByteArrayElements(env,arr,NULL);
int len = (*env)->GetArrayLength(env, arr);
const char *filename = (*env)->GetStringUTFChars(env, texname, 0);
__android_log_print(ANDROID_LOG_INFO, "starwisp", "loading texture");
int id=appLoadTexture(filename,w,h,data);
__android_log_print(ANDROID_LOG_INFO, "starwisp", "loaded texture");
(*env)->ReleaseStringUTFChars(env, texname, filename);
(*env)->ReleaseByteArrayElements(env,arr,data,JNI_ABORT);
}
// create the engine and output mix objects
void Java_foam_starwisp_Scheme_createEngine(JNIEnv* env, jclass clazz)
{
audio_init();
create_audio_engine();
}
#ifndef APP_H_INCLUDED
#define APP_H_INCLUDED
#ifdef __cplusplus
extern "C" {
#endif
#define WINDOW_DEFAULT_WIDTH 640
#define WINDOW_DEFAULT_HEIGHT 480
#define WINDOW_BPP 16
extern void appInit();
extern void initGL();
extern void appDeinit();
extern void appEval(char *code);
extern void appRender(int width, int height);
extern unsigned int appLoadTexture(const char *filename, int width, int height, char* data);
#ifdef __cplusplus
}
#endif
#endif // !APP_H_INCLUDED
......@@ -195,24 +195,26 @@
(define (emit-addr x)
(emit (vector ldl (variable-address (cadr x)) 0)))
;; (if pred true-expr false-expr)
(define (emit-if x)
(let ((tblock (emit-expr (caddr x)))
(fblock (emit-expr (cadddr x))))
(let ((tblock (emit-expr (caddr x))) ;; compile true expression to a block
(fblock (emit-expr (cadddr x)))) ;; compile false expression to block
(append
(emit-expr (cadr x))
(emit (vector jmz (+ (length tblock) 2) 0))
(emit-expr (cadr x)) ;; predicate - returns true or false
(emit (vector jmz (+ (length tblock) 2) 0)) ;; if false skip true block
tblock
(emit (vector jmr (+ (length fblock) 1) 0))
(emit (vector jmr (+ (length fblock) 1) 0)) ;; skip false block
fblock)))
;; (when pred true-block)
(define (emit-when x)
(let ((block (emit-expr-list (cddr x))))
(let ((block (emit-expr-list (cddr x)))) ;; compile the list of expressions
(append
(emit-expr (cadr x))
(emit (vector jmz (+ (length block) 2) 0))
(emit-expr (cadr x)) ;; predicate - returns true or false
(emit (vector jmz (+ (length block) 2) 0)) ;; skip the block
block
(emit (vector jmr 2 0))
(emit (vector ldl 0 0)))))
(emit (vector jmr 2 0)) ;; return result of the block (skip next instr)
(emit (vector ldl 0 0))))) ;; return 0 if we didn't run the block
(define (emit-fncall x addr)
(let ((args (emit-expr-list-maintain-stack (cdr x))))
......
#include <jni.h>
#include <sys/time.h>
#include <time.h>
#include <android/log.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <string.h>
#include <pthread.h>
// for native audio
#include <SLES/OpenSLES.h>
#include <SLES/OpenSLES_Android.h>
//////////////////////////////////////////////77
#include "engine/engine.h"
#include "fluxa/Graph.h"
#include "audio.h"
// audio nonsense
// engine interfaces
static SLObjectItf engineObject = NULL;
static SLEngineItf engineEngine;
// output mix interfaces
static SLObjectItf outputMixObject = NULL;
// buffer queue player interfaces
static SLObjectItf bqPlayerObject = NULL;
static SLPlayItf bqPlayerPlay;
static SLAndroidSimpleBufferQueueItf bqPlayerBufferQueue;
static SLEffectSendItf bqPlayerEffectSend;
static SLMuteSoloItf bqPlayerMuteSolo;
static SLVolumeItf bqPlayerVolume;
// recorder interfaces
static SLObjectItf recorderObject = NULL;
static SLRecordItf recorderRecord;
static SLAndroidSimpleBufferQueueItf recorderBufferQueue;
#define RECORDER_FRAMES (160)
static short recorderBufferA[RECORDER_FRAMES];
static short recorderBufferB[RECORDER_FRAMES];
static short processBuffer[RECORDER_FRAMES];
static unsigned recorderSize = 0;
static int current_buffer=-1;
unsigned int noise_size=1000;
unsigned short *noise;
unsigned int size;
Sample *out_left;
Sample *out_right;
Graph *graph;
void audio_init()
{
WaveTable::WriteWaves();
unsigned int s=RECORDER_FRAMES;
out_left=new Sample(s);
out_right=new Sample(s);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "inner init");
size=s;
graph=engine::get()->get_audio_graph();
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "graph is %d", (int)graph);
}
void audio_process(short *data)
{
out_left->Zero();
out_right->Zero();
graph->Process(size/2,*out_left,*out_right);
unsigned int pos=0;
for (unsigned int i=0; i<size; i+=2)
{
data[i]=(short)((*out_left)[pos++]*3276);
}
pos=0;
for (unsigned int i=1; i<size; i+=2)
{
data[i]=(short)((*out_right)[pos++]*3276);
}
}
// this callback handler is called every time a buffer finishes recording
void bqRecorderCallback(SLAndroidSimpleBufferQueueItf bq, void *context)
{
SLresult result;
current_buffer++;
if (current_buffer>1) current_buffer=0;
short *next_buffer=recorderBufferA;
if (current_buffer==1) next_buffer=recorderBufferB;
result = (*recorderBufferQueue)->Enqueue(recorderBufferQueue, next_buffer,
RECORDER_FRAMES * sizeof(short));
}
void bqPlayerCallback(SLAndroidSimpleBufferQueueItf bq, void *context)
{
short *this_buffer=recorderBufferA;
if (current_buffer==0) this_buffer=recorderBufferB;
memcpy(processBuffer,this_buffer,RECORDER_FRAMES * sizeof(short));
audio_process(processBuffer);
SLresult result; // enqueue another buffer
result = (*bqPlayerBufferQueue)->Enqueue(bqPlayerBufferQueue, processBuffer, RECORDER_FRAMES*sizeof(short));
}
pthread_t audioThread;
void create_player();
void *AudioInOutThread( void *ptr )
{
SLresult result;
create_player();
result = (*bqPlayerBufferQueue)->Enqueue(bqPlayerBufferQueue, recorderBufferA, RECORDER_FRAMES*sizeof(short));
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "enqueue saw play %d", result);
// set the player's state to playing
result = (*bqPlayerPlay)->SetPlayState(bqPlayerPlay, SL_PLAYSTATE_PLAYING);
assert(SL_RESULT_SUCCESS == result);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "started playing %d", result);
}
jboolean setup_recorder()
{
SLresult result;
// configure audio source
SLDataLocator_IODevice loc_dev = {SL_DATALOCATOR_IODEVICE, SL_IODEVICE_AUDIOINPUT,
SL_DEFAULTDEVICEID_AUDIOINPUT, NULL};
SLDataSource audioSrc = {&loc_dev, NULL};
// configure audio sink
SLDataLocator_AndroidSimpleBufferQueue loc_bq = {SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE, 2};
SLDataFormat_PCM format_pcm = {SL_DATAFORMAT_PCM, 1, SL_SAMPLINGRATE_16,
SL_PCMSAMPLEFORMAT_FIXED_16, SL_PCMSAMPLEFORMAT_FIXED_16,
SL_SPEAKER_FRONT_CENTER, SL_BYTEORDER_LITTLEENDIAN};
SLDataSink audioSnk = {&loc_bq, &format_pcm};
// create audio recorder
// (requires the RECORD_AUDIO permission)
const SLInterfaceID id[1] = {SL_IID_ANDROIDSIMPLEBUFFERQUEUE};
const SLboolean req[1] = {SL_BOOLEAN_TRUE};
result = (*engineEngine)->CreateAudioRecorder(engineEngine, &recorderObject, &audioSrc,
&audioSnk, 1, id, req);
if (SL_RESULT_SUCCESS != result) {
return JNI_FALSE;
}
// realize the audio recorder
result = (*recorderObject)->Realize(recorderObject, SL_BOOLEAN_FALSE);
if (SL_RESULT_SUCCESS != result) {
return JNI_FALSE;
}
// get the record interface
result = (*recorderObject)->GetInterface(recorderObject, SL_IID_RECORD, &recorderRecord);
assert(SL_RESULT_SUCCESS == result);
// get the buffer queue interface
result = (*recorderObject)->GetInterface(recorderObject, SL_IID_ANDROIDSIMPLEBUFFERQUEUE,
&recorderBufferQueue);
assert(SL_RESULT_SUCCESS == result);
// register callback on the buffer queue
result = (*recorderBufferQueue)->RegisterCallback(recorderBufferQueue, bqRecorderCallback,
NULL);
assert(SL_RESULT_SUCCESS == result);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "recording set up %d", result);
return JNI_TRUE;
}
// create buffer queue audio player
void create_player()
{
SLresult result;
// configure audio source
SLDataLocator_AndroidSimpleBufferQueue loc_bufq = {SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE, 2};
SLDataFormat_PCM format_pcm = {SL_DATAFORMAT_PCM, 1, SL_SAMPLINGRATE_16,
SL_PCMSAMPLEFORMAT_FIXED_16, SL_PCMSAMPLEFORMAT_FIXED_16,
SL_SPEAKER_FRONT_CENTER, SL_BYTEORDER_LITTLEENDIAN};
SLDataSource audioSrc = {&loc_bufq, &format_pcm};
// configure audio sink
SLDataLocator_OutputMix loc_outmix = {SL_DATALOCATOR_OUTPUTMIX, outputMixObject};
SLDataSink audioSnk = {&loc_outmix, NULL};
// create audio player
const SLInterfaceID ids[3] = {SL_IID_BUFFERQUEUE, SL_IID_EFFECTSEND,
/*SL_IID_MUTESOLO,*/ SL_IID_VOLUME};
const SLboolean req[3] = {SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE,
/*SL_BOOLEAN_TRUE,*/ SL_BOOLEAN_TRUE};
result = (*engineEngine)->CreateAudioPlayer(engineEngine, &bqPlayerObject, &audioSrc, &audioSnk,
3, ids, req);
assert(SL_RESULT_SUCCESS == result);
// realize the player
result = (*bqPlayerObject)->Realize(bqPlayerObject, SL_BOOLEAN_FALSE);
assert(SL_RESULT_SUCCESS == result);
// get the play interface
result = (*bqPlayerObject)->GetInterface(bqPlayerObject, SL_IID_PLAY, &bqPlayerPlay);
assert(SL_RESULT_SUCCESS == result);
// get the buffer queue interface
result = (*bqPlayerObject)->GetInterface(bqPlayerObject, SL_IID_BUFFERQUEUE,
&bqPlayerBufferQueue);
assert(SL_RESULT_SUCCESS == result);
// register callback on the buffer queue
result = (*bqPlayerBufferQueue)->RegisterCallback(bqPlayerBufferQueue, bqPlayerCallback, NULL);
assert(SL_RESULT_SUCCESS == result);
// get the effect send interface
result = (*bqPlayerObject)->GetInterface(bqPlayerObject, SL_IID_EFFECTSEND,
&bqPlayerEffectSend);
assert(SL_RESULT_SUCCESS == result);
#if 0 // mute/solo is not supported for sources that are known to be mono, as this is
// get the mute/solo interface
result = (*bqPlayerObject)->GetInterface(bqPlayerObject, SL_IID_MUTESOLO, &bqPlayerMuteSolo);
assert(SL_RESULT_SUCCESS == result);
#endif
// get the volume interface
result = (*bqPlayerObject)->GetInterface(bqPlayerObject, SL_IID_VOLUME, &bqPlayerVolume);
assert(SL_RESULT_SUCCESS == result);
// set the player's state to playing
result = (*bqPlayerPlay)->SetPlayState(bqPlayerPlay, SL_PLAYSTATE_PLAYING);
assert(SL_RESULT_SUCCESS == result);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "player setup %d", result);
}
void create_audio_engine()
{
SLresult result;
// create engine
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "initEngine");
SLEngineOption EngineOption[] = {(SLuint32) SL_ENGINEOPTION_THREADSAFE, (SLuint32) SL_BOOLEAN_TRUE};
result = slCreateEngine( &engineObject, 1, EngineOption, 0, NULL, NULL);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "create engine result %d", result);
assert(SL_RESULT_SUCCESS == result);
// realize the engine
result = (*engineObject)->Realize(engineObject, SL_BOOLEAN_FALSE);
assert(SL_RESULT_SUCCESS == result);
// get the engine interface, which is needed in order to create other objects
result = (*engineObject)->GetInterface(engineObject, SL_IID_ENGINE, &engineEngine);
assert(SL_RESULT_SUCCESS == result);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "get engine result %d", result);
// create output mix, with environmental reverb specified as a non-required interface
const SLInterfaceID ids[1] = {SL_IID_ENVIRONMENTALREVERB};
const SLboolean req[1] = {SL_BOOLEAN_FALSE};
result = (*engineEngine)->CreateOutputMix(engineEngine, &outputMixObject, 1, ids, req);
assert(SL_RESULT_SUCCESS == result);
// realize the output mix
result = (*outputMixObject)->Realize(outputMixObject, SL_BOOLEAN_FALSE);
assert(SL_RESULT_SUCCESS == result);
result = pthread_create( &audioThread, NULL, AudioInOutThread, NULL);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "created audio playback thread %d", result);
setup_recorder();
// the buffer is not valid for playback yet
recorderSize = 0;
// enqueue an empty buffer to be filled by the recorder
// (for streaming recording, we would enqueue at least 2 empty buffers to start things off)
result = (*recorderBufferQueue)->Enqueue(recorderBufferQueue, recorderBufferA,
RECORDER_FRAMES * sizeof(short));
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "enqueue record A %d", result);
// start recording
result = (*recorderRecord)->SetRecordState(recorderRecord, SL_RECORDSTATE_RECORDING);
assert(SL_RESULT_SUCCESS == result);
__android_log_print(ANDROID_LOG_INFO, "NativeAudio", "started recording %d", result);
}
AC_INIT(myconfig, version-0.1)
echo " Testing for a C compiler"
AC_PROG_CC
echo " Testing for a C++ compiler"
AC_PROG_CXX
AC_LANG(C++)
AC_CHECK_HEADERS(iostream)
AC_CHECK_LIB(m, cos)
AC_CHECK_LIB(glut, main)
AC_CHECK_LIB(gl, main)
AC_CHECK_LIB(png, main)
AC_CHECK_LIB(pthread, main)
AC_CHECK_LIB(dl, main)
AC_CHECK_LIB(lo, main)
AC_CHECK_LIB(jpeg, main)
echo " Are we on Raspberry Pi?"
AC_CHECK_HEADERS(/opt/vc/include/bcm_host.h)
AC_OUTPUT(Makefile)
// Copyright (C) 2013 Dave Griffiths
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program 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 General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "db.h"
#include <stdio.h>
db::db(const char *fn) :
m_running(1)
{
int rc = sqlite3_open(fn, &m_db);
if(rc)
{
m_running=0;
}
}
db::~db()
{
}
sqlite3_stmt *db::prepare(const char *sql)
{
sqlite3_stmt *stmt;
const char *test;
int rc = sqlite3_prepare(m_db, sql, strlen(sql), &stmt, NULL);
if( rc != SQLITE_OK )
{
return NULL;
}
return stmt;
}
void db::bind_text(const char *v, int n, sqlite3_stmt *stmt)
{
sqlite3_bind_text(stmt, n, v, strlen(v), 0);
}
void db::bind_int(int v, int n, sqlite3_stmt *stmt)
{
sqlite3_bind_int(stmt, n, v);
}
void db::bind_float(float v, int n, sqlite3_stmt *stmt)
{
sqlite3_bind_double(stmt, n, (double)v);
}
list *db::run(sqlite3_stmt *stmt)
{
list *data= new list;
bool first=true;
int result=0;
do {
result = sqlite3_step(stmt);
if (result == SQLITE_ROW) { /* can read data */
if (first)
{
// first add the column names
list *row = new list;
for (int i=0; i<sqlite3_column_count(stmt); i++) {
row->add_to_end(new db::value_node(sqlite3_column_name(stmt, i)));
}
data->add_to_end(new db::row_node(row));