summaryrefslogtreecommitdiff
path: root/attic/muse2-oom/muse2/al
diff options
context:
space:
mode:
authorRobert Jonsson <spamatica@gmail.com>2011-03-07 19:01:11 +0000
committerRobert Jonsson <spamatica@gmail.com>2011-03-07 19:01:11 +0000
commite40fc849149dd97c248866a4a1d026dda5e57b62 (patch)
treeb12b358f3b3a0608001d30403358f8443118ec5f /attic/muse2-oom/muse2/al
parent1bd4f2e8d9745cabb667b043171cad22c8577768 (diff)
clean3
Diffstat (limited to 'attic/muse2-oom/muse2/al')
-rw-r--r--attic/muse2-oom/muse2/al/CMakeLists.txt79
-rw-r--r--attic/muse2-oom/muse2/al/al.cpp29
-rw-r--r--attic/muse2-oom/muse2/al/al.h34
-rw-r--r--attic/muse2-oom/muse2/al/dsp.cpp182
-rw-r--r--attic/muse2-oom/muse2/al/dsp.h107
-rw-r--r--attic/muse2-oom/muse2/al/dspSSE.cpp531
-rw-r--r--attic/muse2-oom/muse2/al/dspXMM.cpp119
-rw-r--r--attic/muse2-oom/muse2/al/sig.cpp617
-rw-r--r--attic/muse2-oom/muse2/al/sig.h117
-rw-r--r--attic/muse2-oom/muse2/al/xml.cpp366
-rw-r--r--attic/muse2-oom/muse2/al/xml.h76
11 files changed, 2257 insertions, 0 deletions
diff --git a/attic/muse2-oom/muse2/al/CMakeLists.txt b/attic/muse2-oom/muse2/al/CMakeLists.txt
new file mode 100644
index 00000000..a0031143
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/CMakeLists.txt
@@ -0,0 +1,79 @@
+#=============================================================================
+# MusE
+# Linux Music Editor
+# $Id:$
+#
+# Copyright (C) 2002-2006 by Werner Schweer and others
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2.
+#
+# 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+#=============================================================================
+
+include(${PROJECT_SOURCE_DIR}/pch.txt)
+
+##
+## List of source files to compile
+##
+file (GLOB al_source_files
+ al.cpp
+ dsp.cpp
+ sig.cpp
+ xml.cpp
+ )
+if (USE_SSE)
+ file (GLOB al_source_files
+ ${al_source_files}
+ dspSSE.cpp
+ dspXMM.cpp
+ )
+endif (USE_SSE)
+
+##
+## Define target
+##
+add_library(al SHARED
+ ${PROJECT_BINARY_DIR}/all.h.pch
+ ${al_source_files}
+ )
+
+##
+## Compilation flags and target name
+##
+set_target_properties( al
+ PROPERTIES OUTPUT_NAME muse_al
+ )
+set_source_files_properties(
+ al.cpp
+ dsp.cpp
+ dspXMM.cpp
+ sig.cpp
+ xml.cpp
+ PROPERTIES COMPILE_FLAGS "-fPIC -include ${PROJECT_BINARY_DIR}/all.h"
+ )
+set_source_files_properties(
+ dspSSE.cpp
+ PROPERTIES COMPILE_FLAGS "-x assembler"
+ )
+
+##
+## Linkage
+##
+target_link_libraries ( al
+ ${QT_LIBRARIES}
+ )
+
+##
+## Install location
+##
+install(TARGETS al
+ DESTINATION ${MusE_MODULES_DIR}
+ )
diff --git a/attic/muse2-oom/muse2/al/al.cpp b/attic/muse2-oom/muse2/al/al.cpp
new file mode 100644
index 00000000..38cc301a
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/al.cpp
@@ -0,0 +1,29 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id: al.cpp,v 1.1.2.2 2009/12/06 01:39:33 terminator356 Exp $
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#include "al.h"
+
+namespace AL {
+ //int sampleRate = 44100;
+ //int mtcType = 0;
+ //int division = 384;
+ bool debugMsg = false;
+ };
+
diff --git a/attic/muse2-oom/muse2/al/al.h b/attic/muse2-oom/muse2/al/al.h
new file mode 100644
index 00000000..6f4a07cb
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/al.h
@@ -0,0 +1,34 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id: al.h,v 1.1.2.2 2009/12/06 01:39:33 terminator356 Exp $
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#ifndef __AL_H__
+#define __AL_H__
+
+namespace AL {
+
+ extern bool debugMsg;
+ //extern int sampleRate;
+ //extern int mtcType;
+ //extern int division;
+
+ }
+
+#endif
+
diff --git a/attic/muse2-oom/muse2/al/dsp.cpp b/attic/muse2-oom/muse2/al/dsp.cpp
new file mode 100644
index 00000000..fa9fa18b
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/dsp.cpp
@@ -0,0 +1,182 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id: dsp.cpp,v 1.1.2.1 2009/12/06 01:39:33 terminator356 Exp $
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#include <stdio.h>
+#include <stdint.h>
+#include "dsp.h"
+#include "config.h"
+#include "../globals.h"
+
+namespace AL {
+
+Dsp* dsp = 0;
+
+#ifdef __i386__
+
+//---------------------------------------------------------
+// DspSSE86
+//---------------------------------------------------------
+
+extern "C" {
+extern float x86_sse_compute_peak(float*, unsigned, float);
+extern void x86_sse_apply_gain_to_buffer(float*, unsigned, float);
+extern void x86_sse_mix_buffers_with_gain(float*, float*, unsigned, float);
+extern void x86_sse_mix_buffers_no_gain(float*, float*, unsigned);
+ };
+
+class DspSSE86 : public Dsp {
+ public:
+ DspSSE86() {}
+ virtual ~DspSSE86() {}
+
+ virtual float peak(float* buf, unsigned n, float current) {
+ if ( ((intptr_t)buf % 16) != 0) {
+ fprintf(stderr, "peak(): buffer unaligned! (%p)\n", buf);
+ return Dsp::peak(buf, n, current);
+ }
+ return x86_sse_compute_peak(buf, n, current);
+ }
+
+ virtual void applyGainToBuffer(float* buf, unsigned n, float gain) {
+ if ( ((intptr_t)buf % 16) != 0) {
+ fprintf(stderr, "applyGainToBuffer(): buffer unaligned! (%p)\n", buf);
+ Dsp::applyGainToBuffer(buf, n, gain);
+ }
+ else
+ x86_sse_apply_gain_to_buffer(buf, n, gain);
+ }
+
+ virtual void mixWithGain(float* dst, float* src, unsigned n, float gain) {
+ if ( ((intptr_t)dst & 15) != 0)
+ fprintf(stderr, "mixWithGainain(): dst unaligned! (%p)\n", dst);
+ if (((intptr_t)dst & 15) != ((intptr_t)src & 15) ) {
+ fprintf(stderr, "mixWithGain(): dst & src don't have the same alignment!\n");
+ Dsp::mixWithGain(dst, src,n, gain);
+ }
+ else
+ x86_sse_mix_buffers_with_gain(dst, src, n, gain);
+ }
+ virtual void mix(float* dst, float* src, unsigned n) {
+ if ( ((intptr_t)dst & 15) != 0)
+ fprintf(stderr, "mix_buffers_no_gain(): dst unaligned! %p\n", dst);
+ if ( ((intptr_t)dst & 15) != ((intptr_t)src & 15) ) {
+ fprintf(stderr, "mix_buffers_no_gain(): dst & src don't have the same alignment!\n");
+ Dsp::mix(dst, src, n);
+ }
+ else
+ x86_sse_mix_buffers_no_gain(dst, src, n);
+ }
+ };
+#endif
+
+//---------------------------------------------------------
+// initDsp
+//---------------------------------------------------------
+
+void initDsp()
+ {
+#if 0 // Disabled for now.
+#if defined(__i386__) || defined(__x86_64__)
+ if(debugMsg)
+ printf("Muse: __i386__ or __x86_64__ defined. Using optimized float buffer copying (asm movsl).\n");
+#else
+ if(debugMsg)
+ printf("Muse: __i386__ or __x86_64__ not defined. Using non-optimized memcpy for float buffer copying.\n");
+#endif
+#endif
+
+#if defined(__i386__) && defined(USE_SSE)
+ unsigned long useSSE = 0;
+ if(debugMsg)
+ printf("initDsp: __i386__ and USE_SSE defined\n");
+
+// FIXME: 64? Shouldn't these routines work on 32 bit?
+#ifdef __x86_64__
+ useSSE = 1 << 25; // we know the platform has SSE
+ if(debugMsg)
+ printf("initDsp: __x86_64__ defined\n");
+#else
+ if(debugMsg)
+ printf("initDsp: getting cpuid via asm\n");
+ asm (
+ "mov $1, %%eax\n"
+ "pushl %%ebx\n"
+ "cpuid\n"
+ "movl %%edx, %0\n"
+ "popl %%ebx\n"
+ : "=r" (useSSE)
+ :
+ : "%eax", "%ecx", "%edx", "memory");
+#endif
+ if(debugMsg)
+ printf("initDsp: checking for bit 25 SSE support:%lX\n", useSSE);
+ useSSE &= (1 << 25); // bit 25 = SSE support
+ if (useSSE) {
+ printf("Using SSE optimized routines\n");
+ dsp = new DspSSE86();
+ return;
+ }
+ // fall through to not hardware optimized routines
+#endif
+ if(debugMsg)
+ printf("Muse: using unoptimized non-SSE dsp routines\n");
+ dsp = new Dsp();
+ }
+
+//---------------------------------------------------------
+// exitDsp
+//---------------------------------------------------------
+
+void exitDsp()
+{
+ if(dsp)
+ delete dsp;
+ dsp = 0;
+}
+
+void Dsp::cpy(float* dst, float* src, unsigned n)
+{
+// FIXME: Changed by T356. Not defined. Where are these???
+//#if defined(ARCH_X86) || defined(ARCH_X86_64)
+///#if defined(__i386__) || defined(__x86_64__)
+#if 0 // Disabled for now.
+ //printf("Dsp: using asm cpy\n");
+ // Changed by T356. Get To and From not declared in scope compile errors.
+ //register unsigned long int dummy;
+ //__asm__ __volatile__ ("rep; movsl" :"=&D"(dst), "=&S"(src), "=&c"(dummy) :"0" (to), "1" (from),"2" (n) : "memory");
+ // FIXME: FIXME: I don't think this is correct but it works so far...
+ // Tried clobbering, get "Can't find a register in class `CREG' while reloading `asm'"
+ __asm__ __volatile__ (
+ "cld\n\t"
+ "rep\n\t"
+ "movsl"
+ :
+ : "S" (src), "D" (dst), "c" (n)
+ : "memory"
+ );
+
+ //: "%ecx", "%esi", "%edi", "memory"
+#else
+ //printf("Dsp: using memcpy\n");
+ memcpy(dst, src, sizeof(float) * n);
+#endif
+}
+
+} // namespace AL
diff --git a/attic/muse2-oom/muse2/al/dsp.h b/attic/muse2-oom/muse2/al/dsp.h
new file mode 100644
index 00000000..f88a0122
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/dsp.h
@@ -0,0 +1,107 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id: dsp.h,v 1.1.2.1 2009/12/06 01:39:33 terminator356 Exp $
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#ifndef __DSP_H__
+#define __DSP_H__
+
+#include <string.h>
+#include <math.h>
+
+namespace AL {
+
+//---------------------------------------------------------
+// f_max
+//---------------------------------------------------------
+
+static inline float f_max(float x, float a)
+ {
+ x -= a;
+ x += fabsf(x);
+ x *= 0.5f;
+ x += a;
+ return x;
+ }
+
+//---------------------------------------------------------
+// Dsp
+// standard version of all dsp routines without any
+// hw acceleration
+//---------------------------------------------------------
+
+class Dsp {
+ public:
+ Dsp() {}
+ virtual ~Dsp() {}
+
+ virtual float peak(float* buf, unsigned n, float current) {
+ for (unsigned i = 0; i < n; ++i)
+ current = f_max(current, fabsf(buf[i]));
+ return current;
+ }
+ virtual void applyGainToBuffer(float* buf, unsigned n, float gain) {
+ for (unsigned i = 0; i < n; ++i)
+ buf[i] *= gain;
+ }
+ virtual void mixWithGain(float* dst, float* src, unsigned n, float gain) {
+ for (unsigned i = 0; i < n; ++i)
+ dst[i] += src[i] * gain;
+ }
+ virtual void mix(float* dst, float* src, unsigned n) {
+ for (unsigned i = 0; i < n; ++i)
+ dst[i] += src[i];
+ }
+ virtual void cpy(float* dst, float* src, unsigned n);
+/*
+ {
+// Changed by T356. Not defined. Where are these???
+//#if defined(ARCH_X86) || defined(ARCH_X86_64)
+#if defined(__i386__) || defined(__x86_64__)
+ printf("Dsp: using asm cpy\n");
+ // Changed by T356. Get To and From not declared in scope compile errors.
+ register unsigned long int dummy;
+ //__asm__ __volatile__ ("rep; movsl" :"=&D"(dst), "=&S"(src), "=&c"(dummy) :"0" (to), "1" (from),"2" (n) : "memory");
+ // From http://www.ibiblio.org/gferg/ldp/GCC-Inline-Assembly-HOWTO.html
+ __asm__ __volatile__ ( \
+ "cld\n\t" \
+ "rep\n\t" \
+ "movsl" \
+ : \
+ : "S" (src), "D" (dst), "c" (n) \
+ : "memory"
+ );
+
+ //: "%ecx", "%esi", "%edi", "memory"
+#else
+ printf("Dsp: using memcpy\n");
+ memcpy(dst, src, sizeof(float) * n);
+#endif
+ }
+*/
+
+ };
+
+extern void initDsp();
+extern void exitDsp();
+extern Dsp* dsp;
+
+}
+
+#endif
+
diff --git a/attic/muse2-oom/muse2/al/dspSSE.cpp b/attic/muse2-oom/muse2/al/dspSSE.cpp
new file mode 100644
index 00000000..a345e308
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/dspSSE.cpp
@@ -0,0 +1,531 @@
+//=========================================================
+// MusE
+// Linux Music Editor
+// $Id: dspSSE.cpp,v 1.1.2.3 2009/12/20 00:04:25 spamatica Exp $
+//
+// (C) Copyright 2007-2009 Werner Schweer (ws@seh.de)
+// file originally from Ardour DAW project by Paul Davis (c) 2005
+// licensed through GPL
+// Original author Sampo Savolainen
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//======================================================================
+
+#; void x86_sse_mix_buffers_with_gain (float *dst, float *src, long nframes, float gain);
+
+.globl x86_sse_mix_buffers_with_gain
+ .type x86_sse_mix_buffers_with_gain,@function
+
+x86_sse_mix_buffers_with_gain:
+#; 8(%ebp) = float *dst = %edi
+#; 12(%ebp) = float *src = %esi
+#; 16(%ebp) = long nframes = %ecx
+#; 20(%ebp) = float gain = st(0)
+
+ pushl %ebp
+ movl %esp, %ebp
+
+ #; save the registers
+#; pushl %eax
+ pushl %ebx
+#; pushl %ecx
+ pushl %edi
+ pushl %esi
+
+ #; if nframes == 0, go to end
+ movl 16(%ebp), %ecx #; nframes
+ cmp $0, %ecx
+ je .MBWG_END
+
+ #; Check for alignment
+
+ movl 8(%ebp), %edi #; dst
+ movl 12(%ebp), %esi #; src
+
+ movl %edi, %eax
+ andl $12, %eax #; mask alignemnt offset
+
+ movl %esi, %ebx
+ andl $12, %ebx #; mask alignment offset
+
+ cmp %eax, %ebx
+ jne .MBWG_NONALIGN #; if not aligned, calculate manually
+
+ #; if we are aligned
+ cmp $0, %ebx
+ jz .MBWG_SSE
+
+ #; Pre-loop, we need to run 1-3 frames "manually" without
+ #; SSE instructions
+
+ movss 20(%ebp), %xmm1 #; xmm1
+
+.MBWG_PRELOOP:
+
+ movss (%esi), %xmm0
+ mulss %xmm1, %xmm0
+ addss (%edi), %xmm0
+ movss %xmm0, (%edi)
+
+ addl $4, %edi #; dst++
+ addl $4, %esi #; src++
+ decl %ecx #; nframes--
+ jz .MBWG_END
+
+#; cmp $0, %ecx
+#; je .MBWG_END #; if we run out of frames, go to end
+
+ addl $4, %ebx
+
+ cmp $16, %ebx #; test if we've reached 16 byte alignment
+ jne .MBWG_PRELOOP
+
+
+.MBWG_SSE:
+
+ cmp $4, %ecx #; we know it's not zero, but if it's not >=4, then
+ jnge .MBWG_NONALIGN #; we jump straight to the "normal" code
+
+ #; copy gain to fill %xmm1
+ movss 20(%ebp), %xmm1
+ shufps $0x00, %xmm1, %xmm1
+
+
+.MBWG_SSELOOP:
+
+ movaps (%esi), %xmm0 #; source => xmm0
+ mulps %xmm1, %xmm0 #; apply gain to source
+ addps (%edi), %xmm0 #; mix with destination
+ movaps %xmm0, (%edi) #; copy result to destination
+
+ addl $16, %edi #; dst+=4
+ addl $16, %esi #; src+=4
+
+ subl $4, %ecx #; nframes-=4
+ cmp $4, %ecx
+ jge .MBWG_SSELOOP
+
+ cmp $0, %ecx
+ je .MBWG_END
+
+ #; if there are remaining frames, the nonalign code will do nicely
+ #; for the rest 1-3 frames.
+
+.MBWG_NONALIGN:
+ #; not aligned!
+
+ movss 20(%ebp), %xmm1 #; gain => xmm1
+
+.MBWG_NONALIGNLOOP:
+
+ movss (%esi), %xmm0
+ mulss %xmm1, %xmm0
+ addss (%edi), %xmm0
+ movss %xmm0, (%edi)
+
+ addl $4, %edi
+ addl $4, %esi
+
+ decl %ecx
+ jnz .MBWG_NONALIGNLOOP
+
+.MBWG_END:
+
+ popl %esi
+ popl %edi
+#; popl %ecx
+ popl %ebx
+#; popl %eax
+
+ #; return
+ leave
+ ret
+
+.size x86_sse_mix_buffers_with_gain, .-x86_sse_mix_buffers_with_gain
+
+
+
+
+#; void x86_sse_mix_buffers_no_gain (float *dst, float *src, long nframes);
+
+.globl x86_sse_mix_buffers_no_gain
+ .type x86_sse_mix_buffers_no_gain,@function
+
+x86_sse_mix_buffers_no_gain:
+#; 8(%ebp) = float *dst = %edi
+#; 12(%ebp) = float *src = %esi
+#; 16(%ebp) = long nframes = %ecx
+
+ pushl %ebp
+ movl %esp, %ebp
+
+ #; save the registers
+#; pushl %eax
+ pushl %ebx
+#; pushl %ecx
+ pushl %edi
+ pushl %esi
+
+ #; the real function
+
+ #; if nframes == 0, go to end
+ movl 16(%ebp), %ecx #; nframes
+ cmp $0, %ecx
+ je .MBNG_END
+
+ #; Check for alignment
+
+ movl 8(%ebp), %edi #; dst
+ movl 12(%ebp), %esi #; src
+
+ movl %edi, %eax
+ andl $12, %eax #; mask alignemnt offset
+
+ movl %esi, %ebx
+ andl $12, %ebx #; mask alignment offset
+
+ cmp %eax, %ebx
+ jne .MBNG_NONALIGN #; if not aligned, calculate manually
+
+ cmp $0, %ebx
+ je .MBNG_SSE
+
+ #; Pre-loop, we need to run 1-3 frames "manually" without
+ #; SSE instructions
+
+.MBNG_PRELOOP:
+
+ movss (%esi), %xmm0
+ addss (%edi), %xmm0
+ movss %xmm0, (%edi)
+
+ addl $4, %edi #; dst++
+ addl $4, %esi #; src++
+ decl %ecx #; nframes--
+ jz .MBNG_END
+ addl $4, %ebx
+
+ cmp $16, %ebx #; test if we've reached 16 byte alignment
+ jne .MBNG_PRELOOP
+
+.MBNG_SSE:
+
+ cmp $4, %ecx #; if there are frames left, but less than 4
+ jnge .MBNG_NONALIGN #; we can't run SSE
+
+.MBNG_SSELOOP:
+
+ movaps (%esi), %xmm0 #; source => xmm0
+ addps (%edi), %xmm0 #; mix with destination
+ movaps %xmm0, (%edi) #; copy result to destination
+
+ addl $16, %edi #; dst+=4
+ addl $16, %esi #; src+=4
+
+ subl $4, %ecx #; nframes-=4
+ cmp $4, %ecx
+ jge .MBNG_SSELOOP
+
+ cmp $0, %ecx
+ je .MBNG_END
+
+ #; if there are remaining frames, the nonalign code will do nicely
+ #; for the rest 1-3 frames.
+
+.MBNG_NONALIGN:
+ #; not aligned!
+
+ movss (%esi), %xmm0 #; src => xmm0
+ addss (%edi), %xmm0 #; xmm0 += dst
+ movss %xmm0, (%edi) #; xmm0 => dst
+
+ addl $4, %edi
+ addl $4, %esi
+
+ decl %ecx
+ jnz .MBNG_NONALIGN
+
+.MBNG_END:
+
+ popl %esi
+ popl %edi
+#; popl %ecx
+ popl %ebx
+#; popl %eax
+
+ #; return
+ leave
+ ret
+
+.size x86_sse_mix_buffers_no_gain, .-x86_sse_mix_buffers_no_gain
+
+
+
+
+#; void x86_sse_apply_gain_to_buffer (float *buf, long nframes, float gain);
+
+.globl x86_sse_apply_gain_to_buffer
+ .type x86_sse_apply_gain_to_buffer,@function
+
+x86_sse_apply_gain_to_buffer:
+#; 8(%ebp) = float *buf = %edi
+#; 12(%ebp) = long nframes = %ecx
+#; 16(%ebp) = float gain = st(0)
+
+ pushl %ebp
+ movl %esp, %ebp
+
+ #; save %edi
+ pushl %edi
+
+ #; the real function
+
+ #; if nframes == 0, go to end
+ movl 12(%ebp), %ecx #; nframes
+ cmp $0, %ecx
+ je .AG_END
+
+ #; create the gain buffer in %xmm1
+ movss 16(%ebp), %xmm1
+ shufps $0x00, %xmm1, %xmm1
+
+ #; Check for alignment
+
+ movl 8(%ebp), %edi #; buf
+ movl %edi, %edx #; buf => %edx
+ andl $12, %edx #; mask bits 1 & 2, result = 0, 4, 8 or 12
+ jz .AG_SSE #; if buffer IS aligned
+
+ #; PRE-LOOP
+ #; we iterate 1-3 times, doing normal x87 float comparison
+ #; so we reach a 16 byte aligned "buf" (=%edi) value
+
+.AGLP_START:
+
+ #; Load next value from the buffer
+ movss (%edi), %xmm0
+ mulss %xmm1, %xmm0
+ movss %xmm0, (%edi)
+
+ #; increment buffer, decrement counter
+ addl $4, %edi #; buf++;
+
+ decl %ecx #; nframes--
+ jz .AG_END #; if we run out of frames, we go to the end
+
+ addl $4, %edx #; one non-aligned byte less
+ cmp $16, %edx
+ jne .AGLP_START #; if more non-aligned frames exist, we do a do-over
+
+.AG_SSE:
+
+ #; We have reached the 16 byte aligned "buf" ("edi") value
+
+ #; Figure out how many loops we should do
+ movl %ecx, %eax #; copy remaining nframes to %eax for division
+ movl $0, %edx #; 0 the edx register
+
+
+ pushl %edi
+ movl $4, %edi
+ divl %edi #; %edx = remainder == 0
+ popl %edi
+
+ #; %eax = SSE iterations
+ cmp $0, %eax
+ je .AGPOST_START
+
+
+.AGLP_SSE:
+
+ movaps (%edi), %xmm0
+ mulps %xmm1, %xmm0
+ movaps %xmm0, (%edi)
+
+ addl $16, %edi
+#; subl $4, %ecx #; nframes-=4
+
+ decl %eax
+ jnz .AGLP_SSE
+
+ #; Next we need to post-process all remaining frames
+ #; the remaining frame count is in %ecx
+
+ #; if no remaining frames, jump to the end
+#; cmp $0, %ecx
+ andl $3, %ecx #; nframes % 4
+ je .AG_END
+
+.AGPOST_START:
+
+ movss (%edi), %xmm0
+ mulss %xmm1, %xmm0
+ movss %xmm0, (%edi)
+
+ #; increment buffer, decrement counter
+ addl $4, %edi #; buf++;
+
+ decl %ecx #; nframes--
+ jnz .AGPOST_START #; if we run out of frames, we go to the end
+
+.AG_END:
+
+
+ popl %edi
+
+ #; return
+ leave
+ ret
+
+.size x86_sse_apply_gain_to_buffer, .-x86_sse_apply_gain_to_buffer
+#; end proc
+
+
+
+#; float x86_sse_compute_peak(float *buf, long nframes, float current);
+
+.globl x86_sse_compute_peak
+ .type x86_sse_compute_peak,@function
+
+x86_sse_compute_peak:
+#; 8(%ebp) = float *buf = %edi
+#; 12(%ebp) = long nframes = %ecx
+#; 16(%ebp) = float current = st(0)
+
+ pushl %ebp
+ movl %esp, %ebp
+
+ #; save %edi
+ pushl %edi
+
+ #; the real function
+
+ #; Load "current" in xmm0
+ movss 16(%ebp), %xmm0
+
+ #; if nframes == 0, go to end
+ movl 12(%ebp), %ecx #; nframes
+ cmp $0, %ecx
+ je .CP_END
+
+ #; create the "abs" mask in %xmm2
+ pushl $2147483647
+ movss (%esp), %xmm2
+ addl $4, %esp
+ shufps $0x00, %xmm2, %xmm2
+
+ #; Check for alignment
+
+ movl 8(%ebp), %edi #; buf
+ movl %edi, %edx #; buf => %edx
+ andl $12, %edx #; mask bits 1 & 2, result = 0, 4, 8 or 12
+ jz .CP_SSE #; if buffer IS aligned
+
+ #; PRE-LOOP
+ #; we iterate 1-3 times, doing normal x87 float comparison
+ #; so we reach a 16 byte aligned "buf" (=%edi) value
+
+.LP_START:
+
+ #; Load next value from the buffer
+ movss (%edi), %xmm1
+ andps %xmm2, %xmm1
+ maxss %xmm1, %xmm0
+
+ #; increment buffer, decrement counter
+ addl $4, %edi #; buf++;
+
+ decl %ecx #; nframes--
+ jz .CP_END #; if we run out of frames, we go to the end
+
+ addl $4, %edx #; one non-aligned byte less
+ cmp $16, %edx
+ jne .LP_START #; if more non-aligned frames exist, we do a do-over
+
+.CP_SSE:
+
+ #; We have reached the 16 byte aligned "buf" ("edi") value
+
+ #; Figure out how many loops we should do
+ movl %ecx, %eax #; copy remaining nframes to %eax for division
+
+ shr $2,%eax #; unsigned divide by 4
+ jz .POST_START
+
+ #; %eax = SSE iterations
+
+ #; current maximum is at %xmm0, but we need to ..
+ shufps $0x00, %xmm0, %xmm0 #; shuffle "current" to all 4 FP's
+
+ #;prefetcht0 16(%edi)
+
+.LP_SSE:
+
+ movaps (%edi), %xmm1
+ andps %xmm2, %xmm1
+ maxps %xmm1, %xmm0
+
+ addl $16, %edi
+
+ decl %eax
+ jnz .LP_SSE
+
+ #; Calculate the maximum value contained in the 4 FP's in %xmm0
+ movaps %xmm0, %xmm1
+ shufps $0x4e, %xmm1, %xmm1 #; shuffle left & right pairs (1234 => 3412)
+ maxps %xmm1, %xmm0 #; maximums of the two pairs
+ movaps %xmm0, %xmm1
+ shufps $0xb1, %xmm1, %xmm1 #; shuffle the floats inside the two pairs (1234 => 2143)
+ maxps %xmm1, %xmm0
+
+ #; now every float in %xmm0 is the same value, current maximum value
+
+ #; Next we need to post-process all remaining frames
+ #; the remaining frame count is in %ecx
+
+ #; if no remaining frames, jump to the end
+
+ andl $3, %ecx #; nframes % 4
+ jz .CP_END
+
+.POST_START:
+
+ movss (%edi), %xmm1
+ andps %xmm2, %xmm1
+ maxss %xmm1, %xmm0
+
+ addl $4, %edi #; buf++;
+
+ decl %ecx #; nframes--;
+ jnz .POST_START
+
+.CP_END:
+
+ #; Load the value from xmm0 to the float stack for returning
+ movss %xmm0, 16(%ebp)
+ flds 16(%ebp)
+
+ popl %edi
+
+ #; return
+ leave
+ ret
+
+.size x86_sse_compute_peak, .-x86_sse_compute_peak
+#; end proc
+
+#ifdef __ELF__
+.section .note.GNU-stack,"",%progbits
+#endif
+
+
diff --git a/attic/muse2-oom/muse2/al/dspXMM.cpp b/attic/muse2-oom/muse2/al/dspXMM.cpp
new file mode 100644
index 00000000..99893c3f
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/dspXMM.cpp
@@ -0,0 +1,119 @@
+//=========================================================
+// MusE
+// Linux Music Editor
+// $Id: dspXMM.cpp,v 1.1.2.2 2009/12/20 00:04:25 spamatica Exp $
+//
+// (C) Copyright 2007-2009 Werner Schweer (ws@seh.de)
+// file originally from Ardour DAW project by Paul Davis (c) 2007
+// licensed through GPL
+// Original author Sampo Savolainen
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//======================================================================
+
+
+#include <xmmintrin.h>
+
+void
+x86_sse_find_peaks(float *buf, unsigned nframes, float *min, float *max)
+{
+ __m128 current_max, current_min, work;
+
+ // Load max and min values into all four slots of the XMM registers
+ current_min = _mm_set1_ps(*min);
+ current_max = _mm_set1_ps(*max);
+
+ // Work input until "buf" reaches 16 byte alignment
+ while ( ((unsigned long)buf) % 16 != 0 && nframes > 0) {
+
+ // Load the next float into the work buffer
+ work = _mm_set1_ps(*buf);
+
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+
+ buf++;
+ nframes--;
+ }
+
+ // use 64 byte prefetch for quadruple quads
+ while (nframes >= 16) {
+ __builtin_prefetch(buf+64,0,0);
+
+ work = _mm_load_ps(buf);
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+ buf+=4;
+ work = _mm_load_ps(buf);
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+ buf+=4;
+ work = _mm_load_ps(buf);
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+ buf+=4;
+ work = _mm_load_ps(buf);
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+ buf+=4;
+ nframes-=16;
+ }
+
+ // work through aligned buffers
+ while (nframes >= 4) {
+
+ work = _mm_load_ps(buf);
+
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+
+ buf+=4;
+ nframes-=4;
+ }
+
+ // work through the rest < 4 samples
+ while ( nframes > 0) {
+
+ // Load the next float into the work buffer
+ work = _mm_set1_ps(*buf);
+
+ current_min = _mm_min_ps(current_min, work);
+ current_max = _mm_max_ps(current_max, work);
+
+ buf++;
+ nframes--;
+ }
+
+ // Find min & max value in current_max through shuffle tricks
+
+ work = current_min;
+ work = _mm_shuffle_ps(work, work, _MM_SHUFFLE(2, 3, 0, 1));
+ work = _mm_min_ps (work, current_min);
+ current_min = work;
+ work = _mm_shuffle_ps(work, work, _MM_SHUFFLE(1, 0, 3, 2));
+ work = _mm_min_ps (work, current_min);
+
+ _mm_store_ss(min, work);
+
+ work = current_max;
+ work = _mm_shuffle_ps(work, work, _MM_SHUFFLE(2, 3, 0, 1));
+ work = _mm_max_ps (work, current_max);
+ current_max = work;
+ work = _mm_shuffle_ps(work, work, _MM_SHUFFLE(1, 0, 3, 2));
+ work = _mm_max_ps (work, current_max);
+
+ _mm_store_ss(max, work);
+}
+
+
+
diff --git a/attic/muse2-oom/muse2/al/sig.cpp b/attic/muse2-oom/muse2/al/sig.cpp
new file mode 100644
index 00000000..7eeae6be
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/sig.cpp
@@ -0,0 +1,617 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id:$
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+
+///#include "al.h"
+#include "gconfig.h" // Tim
+#include "sig.h"
+///#include "xml.h"
+
+
+namespace AL {
+
+SigList sigmap;
+
+//---------------------------------------------------------
+// isValid
+//---------------------------------------------------------
+
+bool TimeSignature::isValid() const
+{
+ if((z < 1) || (z > 63))
+ return false;
+
+ switch(n)
+ {
+ case 1:
+ case 2:
+ case 3:
+ case 4:
+ case 8:
+ case 16:
+ case 32:
+ case 64:
+ case 128:
+ return true;
+ default:
+ return false;
+ }
+}
+
+//---------------------------------------------------------
+// SigList
+//---------------------------------------------------------
+
+SigList::SigList()
+ {
+ insert(std::pair<const unsigned, SigEvent*> (MAX_TICK, new SigEvent(TimeSignature(4, 4), 0)));
+ }
+
+//---------------------------------------------------------
+// add
+// signatures are only allowed at the beginning of
+// a bar
+//---------------------------------------------------------
+
+void SigList::add(unsigned tick, const TimeSignature& s)
+ {
+ if (s.z == 0 || s.n == 0) {
+ printf("illegal signature %d/%d\n", s.z, s.n);
+ // Added by Tim.
+ return;
+ }
+ tick = raster1(tick, 0);
+ iSigEvent e = upper_bound(tick);
+ if(e == end())
+ {
+ printf("SigList::add Signal not found tick:%d\n", tick);
+ return;
+ }
+
+ if (tick == e->second->tick) {
+ e->second->sig = s;
+ }
+ else {
+ SigEvent* ne = e->second;
+ SigEvent* ev = new SigEvent(ne->sig, ne->tick);
+ ne->sig = s;
+ ne->tick = tick;
+ insert(std::pair<const unsigned, SigEvent*> (tick, ev));
+ }
+ normalize();
+ }
+
+/*
+void SigList::add(unsigned tick, int z, int n)
+ {
+ if (z == 0 || n == 0) {
+ printf("SigList::add illegal signature %d/%d\n", z, n);
+ // Added by Tim.
+ return;
+ }
+ tick = raster1(tick, 0);
+ iSigEvent e = upper_bound(tick);
+ if(e == end())
+ {
+ printf("SigList::add Signal not found tick:%d\n", tick);
+ return;
+ }
+
+ if (tick == e->second->tick) {
+ e->second->sig.z = z;
+ e->second->sig.n = n;
+ }
+ else {
+ SigEvent* ne = e->second;
+ SigEvent* ev = new SigEvent(ne->sig.z, ne->sig.n, ne->tick);
+ ne->sig.z = z;
+ ne->sig.n = n;
+ ne->tick = tick;
+ insert(std::pair<const unsigned, SigEvent*> (tick, ev));
+ }
+ normalize();
+ }
+*/
+
+//---------------------------------------------------------
+// del
+//---------------------------------------------------------
+
+void SigList::del(unsigned tick)
+ {
+// printf("SigList::del(%d)\n", tick);
+ iSigEvent e = find(tick);
+ if (e == end()) {
+ printf("SigList::del(%d): not found\n", tick);
+ return;
+ }
+ iSigEvent ne = e;
+ ++ne;
+ if (ne == end()) {
+ printf("SigList::del() next event not found!\n");
+ return;
+ }
+ ne->second->sig = e->second->sig;
+ ne->second->tick = e->second->tick;
+ erase(e);
+ normalize();
+ }
+
+//---------------------------------------------------------
+// SigList::normalize
+//---------------------------------------------------------
+
+void SigList::normalize()
+ {
+ TimeSignature sig(0, 0);
+ unsigned tick = 0;
+ iSigEvent ee;
+
+ for (iSigEvent e = begin(); e != end();) {
+ if (sig.z == e->second->sig.z && sig.n == e->second->sig.n) {
+ e->second->tick = tick;
+ erase(ee);
+ }
+ sig = e->second->sig;
+ ee = e;
+ tick = e->second->tick;
+ ++e;
+ }
+
+ int bar = 0;
+ for (iSigEvent e = begin(); e != end();) {
+ e->second->bar = bar;
+ int delta = e->first - e->second->tick;
+ int ticksB = ticks_beat(e->second->sig.n);
+ int ticksM = ticksB * e->second->sig.z;
+ bar += delta / ticksM;
+ if (delta % ticksM) // Teil eines Taktes
+ ++bar;
+ ++e;
+ }
+ }
+
+//---------------------------------------------------------
+// SigList::dump
+//---------------------------------------------------------
+
+void SigList::dump() const
+ {
+ printf("\nSigList:\n");
+ for (ciSigEvent i = begin(); i != end(); ++i) {
+ printf("%6d %06d Bar %3d %02d/%d\n",
+ i->first, i->second->tick,
+ i->second->bar, i->second->sig.z, i->second->sig.n);
+ }
+ }
+
+void SigList::clear()
+ {
+ for (iSigEvent i = begin(); i != end(); ++i)
+ delete i->second;
+ SIGLIST::clear();
+ insert(std::pair<const unsigned, SigEvent*> (MAX_TICK, new SigEvent(TimeSignature(4, 4), 0)));
+ }
+
+//---------------------------------------------------------
+// ticksMeasure
+//---------------------------------------------------------
+
+int SigList::ticksMeasure(const TimeSignature& sig) const
+ {
+ return ticks_beat(sig.n) * sig.z;
+ }
+
+int SigList::ticksMeasure(int Z, int N) const
+ {
+ return ticks_beat(N) * Z;
+ }
+
+int SigList::ticksMeasure(unsigned tick) const
+ {
+ ciSigEvent i = upper_bound(tick);
+ if (i == end()) {
+ printf("ticksMeasure: not found %d\n", tick);
+ // abort();
+ return 0;
+ }
+ return ticksMeasure(i->second->sig);
+ }
+
+//---------------------------------------------------------
+// ticksBeat
+//---------------------------------------------------------
+
+int SigList::ticksBeat(unsigned tick) const
+ {
+ ciSigEvent i = upper_bound(tick);
+ if(i == end())
+ {
+ printf("SigList::ticksBeat event not found! tick:%d\n", tick);
+ return 0;
+ }
+ return ticks_beat(i->second->sig.n);
+ }
+
+int SigList::ticks_beat(int n) const
+ {
+
+ ///int m = AL::division;
+ int m = config.division;
+
+ switch (n) {
+ case 1: m <<= 2; break; // 1536
+ case 2: m <<= 1; break; // 768
+ case 3: m += m >> 1; break; // 384+192
+ case 4: break; // 384
+ case 8: m >>= 1; break; // 192
+ case 16: m >>= 2; break; // 96
+ case 32: m >>= 3; break; // 48
+ case 64: m >>= 4; break; // 24
+ case 128: m >>= 5; break; // 12
+ default: break;
+ }
+ return m;
+ }
+
+//---------------------------------------------------------
+// timesig
+//---------------------------------------------------------
+
+TimeSignature SigList::timesig(unsigned tick) const
+ {
+ ciSigEvent i = upper_bound(tick);
+ if (i == end()) {
+ printf("timesig(%d): not found\n", tick);
+ // abort();
+ return TimeSignature(4,4);
+ }
+ return i->second->sig;
+ }
+
+void SigList::timesig(unsigned tick, int& z, int& n) const
+ {
+ ciSigEvent i = upper_bound(tick);
+ if (i == end()) {
+ printf("timesig(%d): not found\n", tick);
+ // abort();
+ z = 4;
+ n = 4;
+ }
+ else {
+ z = i->second->sig.z;
+ n = i->second->sig.n;
+ }
+ }
+
+//---------------------------------------------------------
+// tickValues
+//---------------------------------------------------------
+
+void SigList::tickValues(unsigned t, int* bar, int* beat, unsigned* tick) const
+ {
+ ciSigEvent e = upper_bound(t);
+ if (e == end()) {
+ fprintf(stderr, "tickValues(0x%x) not found(%zd)\n", t, size());
+ *bar = 0;
+ *beat = 0;
+ *tick = 0;
+ return;
+ }
+
+ int delta = t - e->second->tick;
+ int ticksB = ticks_beat(e->second->sig.n);
+ int ticksM = ticksB * e->second->sig.z;
+ *bar = e->second->bar + delta / ticksM;
+ int rest = delta % ticksM;
+ *beat = rest / ticksB;
+ *tick = rest % ticksB;
+ }
+
+//---------------------------------------------------------
+// bar2tick
+//---------------------------------------------------------
+
+unsigned SigList::bar2tick(int bar, int beat, unsigned tick) const
+ {
+ ciSigEvent e;
+
+ if (bar < 0)
+ bar = 0;
+ for (e = begin(); e != end();) {
+ ciSigEvent ee = e;
+ ++ee;
+ if (ee == end())
+ break;
+ if (bar < ee->second->bar)
+ break;
+ e = ee;
+ }
+ int ticksB = ticks_beat(e->second->sig.n);
+ int ticksM = ticksB * e->second->sig.z;
+ return e->second->tick + (bar-e->second->bar)*ticksM + ticksB*beat + tick;
+ }
+
+//---------------------------------------------------------
+// raster
+//---------------------------------------------------------
+
+unsigned SigList::raster(unsigned t, int raster) const
+ {
+ if (raster == 1)
+ return t;
+ ciSigEvent e = upper_bound(t);
+ if (e == end()) {
+ printf("SigList::raster(%x,)\n", t);
+ // abort();
+ return t;
+ }
+ int delta = t - e->second->tick;
+ int ticksM = ticks_beat(e->second->sig.n) * e->second->sig.z;
+ if (raster == 0)
+ raster = ticksM;
+ int rest = delta % ticksM;
+ int bb = (delta/ticksM)*ticksM;
+ return e->second->tick + bb + ((rest + raster/2)/raster)*raster;
+ }
+
+//---------------------------------------------------------
+// raster1
+// round down
+//---------------------------------------------------------
+
+unsigned SigList::raster1(unsigned t, int raster) const
+ {
+ if (raster == 1)
+ return t;
+ ciSigEvent e = upper_bound(t);
+ if(e == end())
+ {
+ printf("SigList::raster1 event not found tick:%d\n", t);
+ //return 0;
+ return t;
+ }
+
+ int delta = t - e->second->tick;
+ int ticksM = ticks_beat(e->second->sig.n) * e->second->sig.z;
+ if (raster == 0)
+ raster = ticksM;
+ int rest = delta % ticksM;
+ int bb = (delta/ticksM)*ticksM;
+ return e->second->tick + bb + (rest/raster)*raster;
+ }
+
+//---------------------------------------------------------
+// raster2
+// round up
+//---------------------------------------------------------
+
+unsigned SigList::raster2(unsigned t, int raster) const
+ {
+ if (raster == 1)
+ return t;
+ ciSigEvent e = upper_bound(t);
+ if(e == end())
+ {
+ printf("SigList::raster2 event not found tick:%d\n", t);
+ //return 0;
+ return t;
+ }
+
+ int delta = t - e->second->tick;
+ int ticksM = ticks_beat(e->second->sig.n) * e->second->sig.z;
+ if (raster == 0)
+ raster = ticksM;
+ int rest = delta % ticksM;
+ int bb = (delta/ticksM)*ticksM;
+ return e->second->tick + bb + ((rest+raster-1)/raster)*raster;
+ }
+
+//---------------------------------------------------------
+// rasterStep
+//---------------------------------------------------------
+
+int SigList::rasterStep(unsigned t, int raster) const
+ {
+ if (raster == 0) {
+ ciSigEvent e = upper_bound(t);
+ if(e == end())
+ {
+ printf("SigList::rasterStep event not found tick:%d\n", t);
+ //return 0;
+ return raster;
+ }
+
+ return ticks_beat(e->second->sig.n) * e->second->sig.z;
+ }
+ return raster;
+ }
+
+//---------------------------------------------------------
+// SigList::write
+//---------------------------------------------------------
+
+#if 0
+void SigList::write(Xml& xml) const
+ {
+ xml.stag("siglist");
+ for (ciSigEvent i = begin(); i != end(); ++i)
+ i->second->write(xml, i->first);
+ xml.etag("siglist");
+ }
+#endif
+
+void SigList::write(int level, Xml& xml) const
+ {
+ xml.tag(level++, "siglist");
+ for (ciSigEvent i = begin(); i != end(); ++i)
+ i->second->write(level, xml, i->first);
+ xml.tag(level, "/siglist");
+ }
+
+//---------------------------------------------------------
+// SigList::read
+//---------------------------------------------------------
+
+#if 0
+void SigList::read(QDomNode node)
+ {
+ while (!node.isNull()) {
+ QDomElement e = node.toElement();
+ if (e.tagName() == "sig") {
+ SigEvent* t = new SigEvent();
+ unsigned tick = t->read(node);
+ iSigEvent pos = find(tick);
+ if (pos != end())
+ erase(pos);
+ insert(std::pair<const unsigned, SigEvent*> (tick, t));
+ }
+ else
+ printf("MusE:SigList: unknown tag %s\n", e.tagName().toLatin1().constData());
+ node = node.nextSibling();
+ }
+ normalize();
+ }
+#endif
+
+void SigList::read(Xml& xml)
+ {
+ for (;;) {
+ Xml::Token token = xml.parse();
+ const QString& tag = xml.s1();
+ switch (token) {
+ case Xml::Error:
+ case Xml::End:
+ return;
+ case Xml::TagStart:
+ if (tag == "sig") {
+ SigEvent* t = new SigEvent();
+ unsigned tick = t->read(xml);
+ iSigEvent pos = find(tick);
+ if (pos != end())
+ erase(pos);
+ insert(std::pair<const unsigned, SigEvent*> (tick, t));
+ }
+ else
+ xml.unknown("SigList");
+ break;
+ case Xml::Attribut:
+ break;
+ case Xml::TagEnd:
+ if (tag == "siglist") {
+ normalize();
+ return;
+ }
+ default:
+ break;
+ }
+ }
+ }
+
+//---------------------------------------------------------
+// SigEvent::write
+//---------------------------------------------------------
+
+#if 0
+void SigEvent::write(Xml& xml, int at) const
+ {
+ xml.stag(QString("sig at=\"%1\"").arg(at));
+ xml.tag("tick", tick);
+ xml.tag("nom", sig.z);
+ xml.tag("denom", sig.n);
+ xml.etag("sig");
+ }
+#endif
+
+void SigEvent::write(int level, Xml& xml, int at) const
+ {
+ xml.tag(level++, "sig at=\"%d\"", at);
+ xml.intTag(level, "tick", tick);
+ xml.intTag(level, "nom", sig.z);
+ xml.intTag(level, "denom", sig.n);
+ xml.tag(level, "/sig");
+ }
+
+//---------------------------------------------------------
+// SigEvent::read
+//---------------------------------------------------------
+
+#if 0
+int SigEvent::read(QDomNode node)
+ {
+ QDomElement e = node.toElement();
+ int at = e.attribute("at", "0").toInt();
+ node = node.firstChild();
+
+ while (!node.isNull()) {
+ QDomElement e = node.toElement();
+ if (e.tagName() == "tick")
+ tick = e.text().toInt();
+ else if (e.tagName() == "nom")
+ sig.z = e.text().toInt();
+ else if (e.tagName() == "denom")
+ sig.n = e.text().toInt();
+ else
+ printf("MusE:SigEvent: unknown tag %s\n", e.tagName().toLatin1().constData());
+ node = node.nextSibling();
+ }
+ return at;
+ }
+
+}
+#endif
+
+int SigEvent::read(Xml& xml)
+ {
+ int at = 0;
+ for (;;) {
+ Xml::Token token = xml.parse();
+ const QString& tag = xml.s1();
+ switch (token) {
+ case Xml::Error:
+ case Xml::End:
+ return 0;
+ case Xml::TagStart:
+ if (tag == "tick")
+ tick = xml.parseInt();
+ else if (tag == "nom")
+ sig.z = xml.parseInt();
+ else if (tag == "denom")
+ sig.n = xml.parseInt();
+ else
+ xml.unknown("SigEvent");
+ break;
+ case Xml::Attribut:
+ if (tag == "at")
+ at = xml.s2().toInt();
+ break;
+ case Xml::TagEnd:
+ if (tag == "sig")
+ return at;
+ default:
+ break;
+ }
+ }
+ return 0;
+ }
+
+
+} // namespace AL
+
diff --git a/attic/muse2-oom/muse2/al/sig.h b/attic/muse2-oom/muse2/al/sig.h
new file mode 100644
index 00000000..ed18981f
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/sig.h
@@ -0,0 +1,117 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id:$
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#ifndef __SIG_H__
+#define __SIG_H__
+
+#include <map>
+
+#include "../muse/xml.h"
+class Xml;
+
+namespace AL {
+
+#ifndef MAX_TICK
+#define MAX_TICK (0x7fffffff/100)
+#endif
+
+///class Xml;
+
+//---------------------------------------------------------
+// TimeSignature
+//---------------------------------------------------------
+
+struct TimeSignature {
+ int z, n;
+ TimeSignature() { z = 4; n = 4; }
+ TimeSignature(int a, int b) { z = a; n = b; }
+ bool isValid() const;
+ };
+
+//---------------------------------------------------------
+// Signature Event
+//---------------------------------------------------------
+
+struct SigEvent {
+ TimeSignature sig;
+ unsigned tick; // signature valid from this position
+ int bar; // precomputed
+
+ ///int read(QDomNode);
+ ///void write(Xml&, int) const;
+ int read(Xml&);
+ void write(int, Xml&, int) const;
+
+ SigEvent() { }
+ SigEvent(const TimeSignature& s, unsigned tk) {
+ sig = s;
+ tick = tk;
+ bar = 0;
+ }
+ };
+
+//---------------------------------------------------------
+// SigList
+//---------------------------------------------------------
+
+typedef std::map<unsigned, SigEvent*, std::less<unsigned> > SIGLIST;
+typedef SIGLIST::iterator iSigEvent;
+typedef SIGLIST::const_iterator ciSigEvent;
+typedef SIGLIST::reverse_iterator riSigEvent;
+typedef SIGLIST::const_reverse_iterator criSigEvent;
+
+class SigList : public SIGLIST {
+ int ticks_beat(int N) const;
+ void normalize();
+ int ticksMeasure(const TimeSignature&) const;
+ int ticksMeasure(int z, int n) const;
+
+ public:
+ SigList();
+ void clear();
+ void add(unsigned tick, const TimeSignature& s);
+ //void add(unsigned tick, int z, int n);
+ void del(unsigned tick);
+
+ ///void read(QDomNode);
+ ///void write(Xml&) const;
+ void read(Xml&);
+ void write(int, Xml&) const;
+
+ void dump() const;
+
+ TimeSignature timesig(unsigned tick) const;
+ void timesig(unsigned tick, int& z, int& n) const;
+ void tickValues(unsigned t, int* bar, int* beat, unsigned* tick) const;
+ unsigned bar2tick(int bar, int beat, unsigned tick) const;
+
+ int ticksMeasure(unsigned tick) const;
+ int ticksBeat(unsigned tick) const;
+ unsigned raster(unsigned tick, int raster) const;
+ unsigned raster1(unsigned tick, int raster) const; // round down
+ unsigned raster2(unsigned tick, int raster) const; // round up
+ int rasterStep(unsigned tick, int raster) const;
+ };
+
+extern SigList sigmap;
+
+}
+
+#endif
diff --git a/attic/muse2-oom/muse2/al/xml.cpp b/attic/muse2-oom/muse2/al/xml.cpp
new file mode 100644
index 00000000..96489307
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/xml.cpp
@@ -0,0 +1,366 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id:$
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#include "xml.h"
+#include "al.h"
+
+#include <QDomElement>
+#include <QMetaProperty>
+#include <QWidget>
+
+namespace AL {
+
+//---------------------------------------------------------
+// Xml
+//---------------------------------------------------------
+
+Xml::Xml()
+ {
+ level = 0;
+ }
+
+Xml::Xml(QIODevice* device)
+ : QTextStream(device)
+ {
+ setCodec("utf8");
+ level = 0;
+ }
+
+//---------------------------------------------------------
+// putLevel
+//---------------------------------------------------------
+
+void Xml::putLevel()
+ {
+ for (int i = 0; i < level*2; ++i)
+ *this << ' ';
+ }
+
+//---------------------------------------------------------
+// header
+//---------------------------------------------------------
+
+void Xml::header()
+ {
+ *this << "<?xml version=\"1.0\" encoding=\"utf8\"?>" << endl;
+ }
+
+//---------------------------------------------------------
+// put
+//---------------------------------------------------------
+
+void Xml::put(const QString& s)
+ {
+ putLevel();
+ *this << xmlString(s) << endl;
+ }
+
+//---------------------------------------------------------
+// stag
+// <mops attribute="value">
+//---------------------------------------------------------
+
+void Xml::stag(const QString& s)
+ {
+ putLevel();
+ *this << '<' << s << '>' << endl;
+ ++level;
+ }
+
+//---------------------------------------------------------
+// etag
+//---------------------------------------------------------
+
+void Xml::etag(const char* s)
+ {
+ putLevel();
+ *this << "</" << s << '>' << endl;
+ --level;
+ }
+
+//---------------------------------------------------------
+// tagE
+// <mops attribute="value"/>
+//---------------------------------------------------------
+
+void Xml::tagE(const QString& s)
+ {
+ putLevel();
+ *this << '<' << s << "/>" << endl;
+ }
+
+void Xml::tag(const char* name, int val)
+ {
+ putLevel();
+ *this << '<' << name << '>' << val << "</" << name << '>' << endl;
+ }
+
+void Xml::tag(const char* name, unsigned val)
+ {
+ putLevel();
+ *this << '<' << name << '>' << val << "</" << name << '>' << endl;
+ }
+
+void Xml::tag(const char* name, float val)
+ {
+ putLevel();
+ *this << '<' << name << '>' << val << "</" << name << '>' << endl;
+ }
+
+void Xml::tag(const char* name, const double& val)
+ {
+ putLevel();
+ *this << '<' << name << '>' << val << "</" << name << '>' << endl;
+ }
+
+void Xml::tag(const char* name, const QString& val)
+ {
+ putLevel();
+ *this << "<" << name << ">" << xmlString(val) << "</" << name << '>' << endl;
+ }
+
+void Xml::tag(const char* name, const QColor& color)
+ {
+ putLevel();
+ *this << QString("<%1 r=\"%2\" g=\"%3\" b=\"%4\"/>")
+ .arg(name).arg(color.red()).arg(color.green()).arg(color.blue()) << endl;
+ }
+
+void Xml::tag(const char* name, const QWidget* g)
+ {
+ tag(name, QRect(g->pos(), g->size()));
+ }
+
+void Xml::tag(const char* name, const QRect& r)
+ {
+ putLevel();
+ *this << "<" << name;
+ *this << QString(" x=\"%1\" y=\"%2\" w=\"%3\" h=\"%4\"/>")
+ .arg(r.x()).arg(r.y()).arg(r.width()).arg(r.height()) << endl;
+ }
+
+//---------------------------------------------------------
+// xmlString
+//---------------------------------------------------------
+
+QString Xml::xmlString(const QString& ss)
+ {
+ QString s(ss);
+ s.replace('&', "&amp;");
+ s.replace('<', "&lt;");
+ s.replace('>', "&gt;");
+ s.replace('\'', "&apos;");
+ s.replace('"', "&quot;");
+ return s;
+ }
+
+//---------------------------------------------------------
+// readGeometry
+//---------------------------------------------------------
+
+QRect readGeometry(QDomNode node)
+ {
+ QDomElement e = node.toElement();
+ int x = e.attribute("x","0").toInt();
+ int y = e.attribute("y","0").toInt();
+ int w = e.attribute("w","50").toInt();
+ int h = e.attribute("h","50").toInt();
+ return QRect(x, y, w, h);
+ }
+
+//---------------------------------------------------------
+// writeProperties
+//---------------------------------------------------------
+
+void Xml::writeProperties(const QObject* o)
+ {
+ const QMetaObject* meta = o->metaObject();
+
+ //
+ // start from dummy "muse" property, assuming this is the
+ // first muse propertie in widget hierarchy
+ //
+ int from = meta->indexOfProperty("muse") + 1;
+ int n = meta->propertyCount();
+ for (int i = from; i < n; ++i) {
+ QMetaProperty p = meta->property(i);
+ if (!p.isScriptable())
+ continue;
+ const char* name = p.name();
+ QVariant v = p.read(o);
+ switch(v.type()) {
+ case QVariant::Bool:
+ case QVariant::Int:
+ tag(name, v.toInt());
+ break;
+ case QVariant::Double:
+ tag(name, v.toDouble());
+ break;
+ case QVariant::String:
+ tag(name, v.toString());
+ break;
+ case QVariant::Rect:
+ tag(name, v.toRect());
+ break;
+ case QVariant::Point:
+ {
+ QPoint p = v.toPoint();
+ putLevel();
+ *this << "<" << name << QString(" x=\"%1\" y=\"%2\" />")
+ .arg(p.x()).arg(p.y()) << endl;
+ }
+ break;
+
+ default:
+ printf("MusE:%s type %d not implemented\n",
+ meta->className(), v.type());
+ break;
+ }
+ }
+ }
+
+//---------------------------------------------------------
+// readProperties
+//---------------------------------------------------------
+
+void readProperties(QObject* o, QDomNode node)
+ {
+ const QMetaObject* meta = o->metaObject();
+
+ QDomElement e = node.toElement();
+ QString tag(e.tagName());
+ int idx = meta->indexOfProperty(tag.toLatin1().constData());
+ if (idx == -1) {
+ printf("MusE:%s: unknown tag %s\n",
+ meta->className(), tag.toLatin1().constData());
+ return;
+ }
+ QMetaProperty p = meta->property(idx);
+ QVariant v;
+ switch(p.type()) {
+ case QVariant::Int:
+ case QVariant::Bool:
+ v.setValue(e.text().toInt());
+ break;
+ case QVariant::Double:
+ v.setValue(e.text().toDouble());
+ break;
+ case QVariant::String:
+ v.setValue(e.text());
+ break;
+ case QVariant::Rect:
+ v.setValue(AL::readGeometry(node));
+ break;
+ case QVariant::Point:
+ {
+ int x = e.attribute("x","0").toInt();
+ int y = e.attribute("y","0").toInt();
+ v.setValue(QPoint(x, y));
+ }
+ break;
+ default:
+ printf("MusE:%s type %d not implemented\n",
+ meta->className(), p.type());
+ return;
+ }
+ if (p.isWritable())
+ p.write(o, v);
+ }
+
+//---------------------------------------------------------
+// dump
+//---------------------------------------------------------
+
+void Xml::dump(int len, const unsigned char* p)
+ {
+ putLevel();
+ int col = 0;
+ setFieldWidth(5);
+ setNumberFlags(numberFlags() | QTextStream::ShowBase);
+ setIntegerBase(16);
+ for (int i = 0; i < len; ++i, ++col) {
+ if (col >= 16) {
+ setFieldWidth(0);
+ *this << endl;
+ col = 0;
+ putLevel();
+ setFieldWidth(5);
+ }
+ *this << (p[i] & 0xff);
+ }
+ if (col)
+ *this << endl << dec;
+ setFieldWidth(0);
+ setIntegerBase(10);
+ }
+
+//---------------------------------------------------------
+// domError
+//---------------------------------------------------------
+
+void domError(QDomNode node)
+ {
+ QDomElement e = node.toElement();
+ QString tag(e.tagName());
+ QString s;
+ QDomNode dn(node);
+ while (!dn.parentNode().isNull()) {
+ dn = dn.parentNode();
+ const QDomElement e = dn.toElement();
+ const QString k(e.tagName());
+ if (!s.isEmpty())
+ s += ":";
+ s += k;
+ }
+ fprintf(stderr, "%s: Unknown Node <%s>, type %d\n",
+ s.toLatin1().constData(), tag.toLatin1().constData(), node.nodeType());
+ if (node.isText()) {
+ fprintf(stderr, " text node <%s>\n", node.toText().data().toLatin1().constData());
+ }
+ }
+
+//---------------------------------------------------------
+// domNotImplemented
+//---------------------------------------------------------
+
+void domNotImplemented(QDomNode node)
+ {
+ if (!AL::debugMsg)
+ return;
+ QDomElement e = node.toElement();
+ QString tag(e.tagName());
+ QString s;
+ QDomNode dn(node);
+ while (!dn.parentNode().isNull()) {
+ dn = dn.parentNode();
+ const QDomElement e = dn.toElement();
+ const QString k(e.tagName());
+ if (!s.isEmpty())
+ s += ":";
+ s += k;
+ }
+ fprintf(stderr, "%s: Node not implemented: <%s>, type %d\n",
+ s.toLatin1().constData(), tag.toLatin1().constData(), node.nodeType());
+ if (node.isText()) {
+ fprintf(stderr, " text node <%s>\n", node.toText().data().toLatin1().constData());
+ }
+ }
+}
+
diff --git a/attic/muse2-oom/muse2/al/xml.h b/attic/muse2-oom/muse2/al/xml.h
new file mode 100644
index 00000000..a72c1ac5
--- /dev/null
+++ b/attic/muse2-oom/muse2/al/xml.h
@@ -0,0 +1,76 @@
+//=============================================================================
+// AL
+// Audio Utility Library
+// $Id:$
+//
+// Copyright (C) 2002-2006 by Werner Schweer and others
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License version 2.
+//
+// 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+//=============================================================================
+
+#ifndef __XML_H__
+#define __XML_H__
+
+#include <QTextStream>
+
+class QColor;
+class QDomNode;
+class QRect;
+class QWidget;
+
+namespace AL {
+
+//---------------------------------------------------------
+// Xml
+//---------------------------------------------------------
+
+class Xml : public QTextStream {
+ int level;
+
+ public:
+ Xml();
+ Xml(QIODevice*);
+
+ void header();
+ void putLevel();
+
+ void put(const QString&);
+
+ void stag(const QString&);
+ void etag(const char*);
+
+ void tagE(const QString&);
+
+ void tag(const char* name, int);
+ void tag(const char* name, unsigned);
+ void tag(const char* name, const double& val);
+ void tag(const char* name, float val);
+ void tag(const char* name, const QString& s);
+ void tag(const char* name, const QColor& color);
+ void tag(const char* name, const QWidget* g);
+ void tag(const char* name, const QRect& r);
+
+ void dump(int n, const unsigned char*);
+ void writeProperties(const QObject*);
+
+ static QString xmlString(const QString&);
+ };
+
+extern QRect readGeometry(QDomNode);
+extern void readProperties(QObject* o, QDomNode node);
+extern void domError(QDomNode node);
+extern void domNotImplemented(QDomNode node);
+}
+
+#endif
+