Apostolos\’ Daily Plate

Είναι τρελοί αυτοί οι Ρωμιοί!

Posted in «Αθλητισμός» by asyropoulos on Ιουλίου 21, 2015

Το ότι το Ελλαδικό Δημόσιο και ειδικότερα οι Εφορίες είναι φρενοκομεία το ξέρουν όλοι. Αλλά αυτό που μου συνέβη πρόσφατα δεν έχει προηγούμενο. Επειδή έκανα μια τροποιητική δήλωση, γιατί απλά κάποιος που με πλήρωσε 55€ έβαλε το ποσό σε λάθος κωδικό. Έτσι τα ελλαδικά φρενοκομεία βρήκαν επιτέλους τον μεγαλοφοροφυγά και τον υποχρεώνουν να πάει όλα τα χαρτιά στην ιερά εξέταση του τοπικού φρενοκομείου! Το δε TAXIS απλά κάνει τον Πόντιο Πιλάτο, τι άλλο θα μπορούσε να κάνει αφού είναι μέρος του συστήματος. Για του λόγου το αληθές δείτε τι μου απαντήσαν:

TROPOIHTIKHΕίναι κρίμα αλλά η χώρα δεν έχει καμία ελπίδα.

Να μια ιδέα!

Posted in Χωρίς κατηγορία by asyropoulos on Ιουλίου 4, 2015

IMF

Γιατί να διδάσκεται η πληροφορική;

Posted in Επιστήμη, Πληροφορική by asyropoulos on Μαΐου 6, 2015

Διάβασα το παρακάτω σχόλιο και κατάλαβα πόσο βαθιά νυχτωμένος είναι ο λαός μας…

 

Bullshit2

Αφού υπάρχουν όλα τα προγράμματα, τι να πω εγώ;

Για όλα φταίνε τα μνημόνια

Posted in «Αθλητισμός», Πολιτικά by asyropoulos on Μαΐου 6, 2015

Πολύ χαμηλού επιπέδου «Μαρξιστική» ανάλυση:

Bullshit

Κρίμα!

Best Practices in (computer) Education

Posted in Επιστήμη, Πληροφορική by asyropoulos on Απριλίου 23, 2015

Every year there is a competition about best practices in (computer) education. This competition has a prize of EUR 5,000.00, funded through a Microsoft grant. Obviously, such a competition is doomed  to promote things that are do not harm Microsoft’s image in any way. For example, how can one propose the use of, say, Ubuntu Linux as an educational environment in a competition founded by Microsoft?  In addition, I have noticed that all awards go to University people who have nothing to do with high school education. How can one propose something that cannot be tested in classrooms? In most cases, schools have to follow curricula that are imposed my the ministry of education. Therefore, schools do not have any flexibility to follow different ideas and/or methodologies.

Is the Pestalozzi Program a Lottery?

Posted in «Αθλητισμός», Διάφορα, Παιδεία by asyropoulos on Μαρτίου 31, 2015

This year I applied to participate in a «training event» of the Pestalozzi Program. Applicants had to fill in an on-line form. The form had various fields including one’s education and some optional fields about the way one intends to contribute to the program. I did not read carefully enough the «call for applications» posted by the Greek Ministry of Education so I was not aware of an important detail. When the results of the national selection procedure were published I was surprised because they did not explain the reason why my application was rejected. I sent them an e-mail asking for an explanation. They called me back and they told me that my application was not rejected but rather they drew lots to see which applications should be selected! Interestingly, the people of the Pestalozzi Program sent me the following email:

COE

So «considered carefully» means draw lots?  Go Europe, go!

Εθνικό αρχαιολογικό μουσείο…

Posted in «Αθλητισμός», Επιστήμη by asyropoulos on Μαρτίου 12, 2015

Γράφω ένα εκλαϊκευμένο βιβλίο με θέμα της έννοια του υπολογισμού. Στο πρώτο κεφάλαιο του βιβλίου υπάρχει μια παρουσίαση παλιών υπολογιστικών συσκευών. Ένας από τους κριτές της αρχικής πρότασης (book proposal) μου ζήτησε να βάλω και εικόνες διαφόρων «αρχαίων» υπολογιστικών συσκευών. Έγραψα σε 2 Ιταλικά μουσεία, ένα βρετανικό και στο εθνικό αρχαιολογικό μουσείο. Τα Ιταλικά ήδη μου απάντησαν. Το ένα μου έδωσε ήδη το υλικό και το δεύτερο που χρέωνε για το υλικό μου ζήτησε να συμπληρώσω μια αίτηση ώστε να μου παρέχουν δωρεάν το υλικό. Επίσης, μετά από δύο μέρες μου απάντησε και το βρετανικό. Το ελληνικό μoυσείο μου απάντησε μετά από 11 ημέρες με ένα e-mail που θυμίζει περισσότερο έγγραφο του Ελλαδικού Δημοσίου παρά ένα απλό e-mail (το μήνυμα έχει μάλιστα και «Αρ. Πρωτ. 3048»!). Στο μήνυμα αυτό με ενημερώναν πως μου δίνουν δικαίωμα να βάλω την φωτογραφία που θέλω αλλά δεν μου στείλανε την φωτογραφία. Στο ίδιο μήυνυμα μου ζητούσαν επιπλεόν πληροφορίες τις οποίες και έστειλα στις 18 Μαρτίου (σήμερα έχουμε 31 Μαρτίου) αλλά δεν έχω λάβει απάντηση μέχρι σήμερα. Μόλις λάβω απάντηση, θα συμπληρώσω το άρθρο.

ΥΓ Στις 2 Απριλίου 2015 έστειλα ένα e-mail στο Deutsches Museum στο οποίο τοτς ζητούσα να μου δοθεί άδεια να βάλω μία φωτογραφία της αριθμομηχανής του Leibniz. Μου απαντήσαν στις 8 Απρλίου. Στις 10 Απριλίου τελείωσαν τα διαδικαστικά και τώρα περιμένω την φωτογραφία η οποία λογικά θα μου αποσταλεί στις 13 Απριλίου. Από το Εθνικό Αρχαιολογικό Μουσείο ούτε φωνή, ούτε ακρόαση.

 

ΥΓ2 Σήμερα είκναι 6 Μαΐου 2015 και έχω αγοράσει ή πάρει δωρεάν φωτό από 5-6 μουσεία από τις ΗΠΑ, Γαλλία, Αγγλία, Γερμανία και Ιταλία αλλά δεν φυσικά δεν έλαβα καμία απάντηση από Εθνικό Αρχαιολογικό Μουσείο. Μου έμεινε βεβαια ο αριθμός πρωτοκόλλου.

Παν μέτρον άριστον ή Μέτρον άριστον;

Posted in «Αθλητισμός» by asyropoulos on Μαρτίου 7, 2015

Ήθελα να απαντήσω στο status στο Facebook ενός μη-ελληνόφωνου φίλου με το γνωστό «Παν μέτρον άριστον». Δεν ήξερα αν υπάρχει έκφραση αντίστοιχη στα Αγγλικά και φυσικά το έψαξα με το Google. Η πρώτη σελίδα που μου βγήκε είναι από την Wikepedia αλλά πουθενά δεν υπάρχει το Παν Μέτρον Άριστον αλλά υπάρχει Μέτρον Άριστον. Η αλήθεια είναι πως αυτή είναι έκφραση, η άλλη είναι άλλη μια σαχλαμάρα κάποιων ελληναράδων. Μου αρέσει όμως που διδάσκεται η νεολαία αρχαία ελληνικά και που ξέρουμε την γλώσσα των προγόνων μας και άλλα τέτοια απίθανα κουλά. Να και η σελίδα στη Wikipedia: http://en.wikipedia.org/wiki/List_of_Greek_phrases

Μητέρες ανηλίκων!

Posted in «Αθλητισμός» by asyropoulos on Φεβρουαρίου 15, 2015

Δεν θεωρώ πως οι εργαζόμενοι πρέπει να βγαίνουν στη σύνταξη στα 67 αλλά θεωρώ πως όλοι πρέπει να βγαίνουν στη σύνατξη στα 60 ετός βέβαια από αυτούς που αποδεδειγμένα εργάζονται σε αντίξοες συνθήκες, όπως ορυχεία κ.λπ. Όμως πάντα θεωρούσα παράλογο αυτό που συμβαίνει στη Δημόσιο της  χώρα μας όπου μητέρες με ανήλικα 16 και 17 ετών βγαίνουν στη σύνταξη ως μητρέρες ανηλίκων! Πολύ απλά είναι τεράστια αδικία για εργαζόμενες που κάναν παιδιά μικρές και φυσικά δεν τους  «πιάνει» το μέτρο. Από την άλλη είναι ένα μέτρο με ηλίθιο σκεπτικό επειδή αν μια εργαζόμενη έχει ανήλικο παιδί πρέπει το κράτος να φροντίζει για παιδικούς σταθμούς και νηπιαγωγεία και όχι να δίνει σύνταξη σε εργαζόμενες 40 και 45 ετών! Δυστυχώς, τέτοιες «στρεβλώσεις» βλέπουν οι διάφοροι καλοθελητές και μας χαρακτηρίζουν ως έθνος τεμπέλιδων.

Compiling pulseaudio-5.99.3 on Solaris x86

Posted in Πληροφορική, OpenIndiana, OpenSolaris by asyropoulos on Φεβρουαρίου 9, 2015

Oracle has released some patches that can be used to compile a very old version of PulseAudio. I have used these patches and after adding some things and removing some others I have successfully managed to compile Pulse Audio. The patches follows:


diff -rupN pulseaudio-5.99.3.old/src/daemon/default.pa.in pulseaudio-5.99.3/src/daemon/default.pa.in
--- pulseaudio-5.99.3.old/src/daemon/default.pa.in 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/daemon/default.pa.in 2015-02-08 22:11:11.577334805 +0200
@@ -54,7 +54,7 @@ ifelse(@HAVE_ALSA@, 1, [dnl
#load-module module-alsa-source device=hw:1,0
])dnl
ifelse(@HAVE_OSS_OUTPUT@, 1, [dnl
-#load-module module-oss device="/dev/dsp" sink_name=output source_name=input
+load-module module-oss device="/dev/dsp" sink_name=output source_name=input
#load-module module-oss-mmap device="/dev/dsp" sink_name=output source_name=input
])dnl
ifelse(@HAVE_WAVEOUT@, 1, [dnl
diff -rupN pulseaudio-5.99.3.old/src/daemon/esdcompat.in pulseaudio-5.99.3/src/daemon/esdcompat.in
--- pulseaudio-5.99.3.old/src/daemon/esdcompat.in 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/daemon/esdcompat.in 2015-02-08 22:11:11.577649151 +0200
@@ -88,7 +88,10 @@ EOF
;;
esac

– shift
+ # don’t try to shift nonexisting args
+ if [ $1 ]; then
+ shift
+ fi
done

eval «exec ‘@PA_BINARY@’$ARGS»
diff -rupN pulseaudio-5.99.3.old/src/modules/gconf/module-gconf.c pulseaudio-5.99.3/src/modules/gconf/module-gconf.c
— pulseaudio-5.99.3.old/src/modules/gconf/module-gconf.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/gconf/module-gconf.c 2015-02-08 22:11:11.578283648 +0200
@@ -56,7 +56,7 @@ struct module_item {
uint32_t index;
};

-struct module_info {
+struct pa_module_info {
struct userdata *userdata;
char *name;

@@ -129,7 +129,7 @@ static char *read_string(struct userdata
}
}

-static void unload_one_module(struct module_info *m, unsigned i) {
+static void unload_one_module(struct pa_module_info *m, unsigned i) {
struct userdata *u;

pa_assert(m);
@@ -148,7 +148,7 @@ static void unload_one_module(struct mod
m->items[i].name = m->items[i].args = NULL;
}

-static void unload_all_modules(struct module_info *m) {
+static void unload_all_modules(struct pa_module_info *m) {
unsigned i;

pa_assert(m);
@@ -160,7 +160,7 @@ static void unload_all_modules(struct mo
}

static void load_module(
– struct module_info *m,
+ struct pa_module_info *m,
unsigned i,
const char *name,
const char *args,
@@ -199,7 +199,7 @@ static void load_module(
}

static void module_info_free(void *p) {
– struct module_info *m = p;
+ struct pa_module_info *m = p;

pa_assert(m);

@@ -227,14 +227,14 @@ static int handle_event(struct userdata

case ‘+’: {
char *name;
– struct module_info *m;
+ struct pa_module_info *m;
unsigned i, j;

if (!(name = read_string(u)))
goto fail;

if (!(m = pa_hashmap_get(u->module_infos, name))) {
– m = pa_xnew(struct module_info, 1);
+ m = pa_xnew(struct pa_module_info, 1);
m->userdata = u;
m->name = name;
m->n_items = 0;
diff -rupN pulseaudio-5.99.3.old/src/modules/module-augment-properties.c pulseaudio-5.99.3/src/modules/module-augment-properties.c
— pulseaudio-5.99.3.old/src/modules/module-augment-properties.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/module-augment-properties.c 2015-02-08 22:11:11.578666761 +0200
@@ -158,8 +158,8 @@ static void update_rule(struct rule *r)
/* Let’s try a more aggressive search, but only one level */
if ((desktopfiles_dir = opendir(DESKTOPFILEDIR))) {
while ((dir = readdir(desktopfiles_dir))) {
– if (dir->d_type != DT_DIR
– || pa_streq(dir->d_name, «.»)
+ if (/* dir->d_type != DT_DIR
+ || */ pa_streq(dir->d_name, «.»)
|| pa_streq(dir->d_name, «..»))
continue;

diff -rupN pulseaudio-5.99.3.old/src/modules/module-solaris.c pulseaudio-5.99.3/src/modules/module-solaris.c
— pulseaudio-5.99.3.old/src/modules/module-solaris.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/module-solaris.c 2015-02-08 22:11:11.579626929 +0200
@@ -135,6 +135,7 @@ static const char* const valid_modargs[]
static uint64_t get_playback_buffered_bytes(struct userdata *u) {
audio_info_t info;
uint64_t played_bytes;
+ int64_t buffered_bytes;
int err;

pa_assert(u->sink);
@@ -161,10 +162,13 @@ static uint64_t get_playback_buffered_by

pa_smoother_put(u->smoother, pa_rtclock_now(), pa_bytes_to_usec(played_bytes, &u->sink->sample_spec));

– if (u->written_bytes > played_bytes)
– return u->written_bytes – played_bytes;
– else
– return 0;
+ buffered_bytes = u->written_bytes – played_bytes;
+
+ if (buffered_bytes < 0) {
+ buffered_bytes = 0;
+ }
+
+ return (uint64_t) buffered_bytes;
}

static pa_usec_t sink_get_latency(struct userdata *u, pa_sample_spec *ss) {
@@ -415,7 +419,7 @@ static int sink_process_msg(pa_msgobject
if (unsuspend(u) < 0) return -1; u->sink->get_volume(u->sink);
– u->sink->get_mute(u->sink);
+ u->sink->get_mute(u->sink,(_Bool*)1);
}
u->sink_suspended = false;
}
@@ -486,14 +490,26 @@ static int source_process_msg(pa_msgobje
static void sink_set_volume(pa_sink *s) {
struct userdata *u;
audio_info_t info;
+ pa_volume_t v;

pa_assert_se(u = s->userdata);

+ if (u->fd < 0) { + u->fd = pa_open_cloexec(u->device_name, u->mode | O_NONBLOCK, 0);
+ }
+
if (u->fd >= 0) {
AUDIO_INITINFO(&info);

– info.play.gain = pa_cvolume_max(&s->real_volume) * AUDIO_MAX_GAIN / PA_VOLUME_NORM;
– pa_assert(info.play.gain <= AUDIO_MAX_GAIN); + v = pa_cvolume_max(&s->real_volume);
+ if (v > PA_VOLUME_NORM) {
+ v = PA_VOLUME_NORM;
+ }
+
+ info.play.gain = v * AUDIO_MAX_GAIN / PA_VOLUME_NORM;
+
+ pa_log_debug(«PA_VOLUME_NORM is %ld», PA_VOLUME_NORM);
+ pa_log_debug(«Setting volume %ld %ld», v, info.play.gain);

if (ioctl(u->fd, AUDIO_SETINFO, &info) < 0) { if (errno == EINVAL) @@ -513,22 +529,29 @@ static void sink_get_volume(pa_sink *s) if (u->fd >= 0) {
if (ioctl(u->fd, AUDIO_GETINFO, &info) < 0) pa_log(«AUDIO_SETINFO: %s», pa_cstrerror(errno)); – else + else { + pa_log_debug(«Getting volume %ld %ld», info.play.gain, (info.play.gain * PA_VOLUME_NORM / AUDIO_MAX_GAIN)); pa_cvolume_set(&s->real_volume, s->sample_spec.channels, info.play.gain * PA_VOLUME_NORM / AUDIO_MAX_GAIN);
+ }
}
}

static void source_set_volume(pa_source *s) {
struct userdata *u;
audio_info_t info;
+ pa_volume_t v;

pa_assert_se(u = s->userdata);

if (u->fd >= 0) {
AUDIO_INITINFO(&info);

– info.play.gain = pa_cvolume_max(&s->real_volume) * AUDIO_MAX_GAIN / PA_VOLUME_NORM;
– pa_assert(info.play.gain <= AUDIO_MAX_GAIN); + v = pa_cvolume_max(&s->real_volume);
+ if (v > PA_VOLUME_NORM) {
+ v = PA_VOLUME_NORM;
+ }
+
+ info.play.gain = v * AUDIO_MAX_GAIN / PA_VOLUME_NORM;

if (ioctl(u->fd, AUDIO_SETINFO, &info) < 0) { if (errno == EINVAL) @@ -1034,7 +1057,7 @@ int pa__init(pa_module *m) { if (sink_new_data.muted_is_set) u->sink->set_mute(u->sink);
else
– u->sink->get_mute(u->sink);
+ u->sink->get_mute(u->sink,(_Bool*)1);

pa_sink_put(u->sink);
}
diff -rupN pulseaudio-5.99.3.old/src/modules/oss/module-oss.c pulseaudio-5.99.3/src/modules/oss/module-oss.c
— pulseaudio-5.99.3.old/src/modules/oss/module-oss.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/oss/module-oss.c 2015-02-08 22:11:11.581263125 +0200
@@ -32,6 +32,10 @@
*
*/

+#define HAVE_OSSV4
+#define TRUE 1
+#define FALSE 0
+
#ifdef HAVE_CONFIG_H
#include
#endif
@@ -123,7 +127,18 @@ struct userdata {
int mode;

int mixer_fd;
+
+#ifdef HAVE_OSSV4
+ int mixer_dev;
+ int mixer_sink_control;
+ int mixer_source_control;
+ int mixer_cmax;
+ int mixer_dsp_fd;
+ oss_mixext sink_mixext;
+ oss_mixext source_mixext;
+#else
int mixer_devmask;
+#endif

int nfrags, frag_size, orig_frag_size;

@@ -809,6 +824,160 @@ static int source_process_msg(pa_msgobje
return ret;
}

+#ifdef HAVE_OSSV4
+
+static const char *
+mixer_ext_type_get_name (int type)
+{
+ switch (type) {
+ case MIXT_DEVROOT:
+ return «Device root entry»;
+ case MIXT_GROUP:
+ return «Controller group»;
+ case MIXT_ONOFF:
+ return «On/Off switch»;
+ case MIXT_ENUM:
+ return «Enumeration control»;
+ case MIXT_MONOSLIDER:
+ return «Mono slider (0-255)»;
+ case MIXT_STEREOSLIDER:
+ return «Stereo slider (0-255)»;
+ case MIXT_MESSAGE:
+ return «Textual message»;
+ case MIXT_MONOVU:
+ return «Mono VU meter value»;
+ case MIXT_STEREOVU:
+ return «Stereo VU meter value»;
+ case MIXT_MONOPEAK:
+ return «Mono VU meter peak value»;
+ case MIXT_STEREOPEAK:
+ return «Stereo VU meter peak value»;
+ case MIXT_RADIOGROUP:
+ return «Radio button group»;
+ case MIXT_MARKER:
+ /* Separator between normal and extension entries */
+ return «Separator»;
+ case MIXT_VALUE:
+ return «Decimal value entry»;
+ case MIXT_HEXVALUE:
+ return «Hex value entry»;
+ case MIXT_SLIDER:
+ return «Mono slider (31-bit value range)»;
+ case MIXT_3D:
+ return «3D»;
+ case MIXT_MONOSLIDER16:
+ return «Mono slider (0-32767)»;
+ case MIXT_STEREOSLIDER16:
+ return «Stereo slider (0-32767)»;
+ case MIXT_MUTE:
+ return «Mute switch»;
+ default:
+ break;
+ }
+
+ return «Unknown»;
+}
+
+void
+mixer_showflags (int flags)
+{
+ struct
+ {
+ int flag;
+ char nick[16];
+ } all_flags[] = {
+ /* first the important ones */
+ {
+ MIXF_MAINVOL, «MAINVOL»}, {
+ MIXF_PCMVOL, «PCMVOL»}, {
+ MIXF_RECVOL, «RECVOL»}, {
+ MIXF_MONVOL, «MONVOL»}, {
+ MIXF_DESCR, «DESCR»},
+
+ /* now the rest in the right order */
+ {
+ MIXF_READABLE, «READABLE»}, {
+ MIXF_WRITEABLE, «WRITABLE»}, {
+ MIXF_POLL, «POLL»}, {
+ MIXF_HZ, «HZ»}, {
+ MIXF_STRING, «STRING»}, {
+ MIXF_DYNAMIC, «DYNAMIC»}, {
+ MIXF_OKFAIL, «OKFAIL»}, {
+ MIXF_FLAT, «FLAT»}, {
+ MIXF_LEGACY, «LEGACY»}, {
+ MIXF_CENTIBEL, «CENTIBEL»}, {
+ MIXF_DECIBEL, «DECIBEL»}, {
+ MIXF_WIDE, «WIDE»}
+ };
+ int num_flags = (sizeof (all_flags) / sizeof ((all_flags)[0]));
+ int i;
+
+ if (flags == 0) {
+ pa_log_debug (» flags : None»);
+ return;
+ }
+
+ for (i=0; i < num_flags; i++) { + if ((flags & all_flags[i].flag)) { + pa_log_debug (» flag : %s», all_flags[i].nick); + flags &= ~all_flags[i].flag; /* unset */ + } + } + + /* Unknown flags? */ + if (flags != 0) { + pa_log_debug (» flag : ????»); + } + + return; +} + +static void sink_get_volume(pa_sink *s) { + struct userdata *u; + + pa_assert_se(u = s->userdata);
+
+ if (pa_oss_get_volume(u->mixer_dsp_fd, &(u->sink_mixext), &s->sample_spec, &s->real_volume) >= 0)
+ return;
+
+ pa_log_info(«Device doesn’t support reading mixer settings: %s», pa_cstrerror(errno));
+}
+
+static void sink_set_volume(pa_sink *s) {
+ struct userdata *u;
+
+ pa_assert_se(u = s->userdata);
+
+ if (pa_oss_set_volume(u->mixer_dsp_fd, &(u->sink_mixext), &s->sample_spec, &s->real_volume) >= 0)
+ return;
+
+ pa_log_info(«Device doesn’t support writing mixer settings: %s», pa_cstrerror(errno));
+}
+
+static void source_get_volume(pa_source *s) {
+ struct userdata *u;
+
+ pa_assert_se(u = s->userdata);
+
+ if (pa_oss_get_volume(u->mixer_dsp_fd, &(u->source_mixext), &s->sample_spec, &s->real_volume) >= 0)
+ return;
+
+ pa_log_info(«Device doesn’t support reading mixer settings: %s», pa_cstrerror(errno));
+}
+
+static void source_set_volume(pa_source *s) {
+ struct userdata *u;
+
+ pa_assert_se(u = s->userdata);
+
+ if (pa_oss_set_volume(u->mixer_dsp_fd, &(u->source_mixext), &s->sample_spec, &s->real_volume) >= 0)
+ return;
+
+ pa_log_info(«Device doesn’t support writing mixer settings: %s», pa_cstrerror(errno));
+}
+
+#else
+
static void sink_get_volume(pa_sink *s) {
struct userdata *u;

@@ -880,6 +1049,7 @@ static void source_set_volume(pa_source

pa_log_info(«Device doesn’t support writing mixer settings: %s», pa_cstrerror(errno));
}
+#endif

static void thread_func(void *userdata) {
struct userdata *u = userdata;
@@ -1162,6 +1332,11 @@ finish:

int pa__init(pa_module*m) {

+#ifdef HAVE_OSSV4
+ struct oss_sysinfo si = { {0,}, };
+ struct oss_mixerinfo mi = { 0, };
+#endif
+
struct audio_buf_info info;
struct userdata *u = NULL;
const char *dev;
@@ -1259,7 +1434,9 @@ int pa__init(pa_module*m) {
m->userdata = u;
u->fd = fd;
u->mixer_fd = -1;
+#ifndef HAVE_OSSV4
u->mixer_devmask = 0;
+#endif
u->use_getospace = u->use_getispace = true;
u->use_getodelay = true;
u->mode = mode;
@@ -1426,6 +1603,194 @@ int pa__init(pa_module*m) {
if ((u->mixer_fd = pa_oss_open_mixer_for_device(u->device_name)) >= 0) {
bool do_close = true;

+#ifdef HAVE_OSSV4
+#define IGNORE_DEV 1
+ int i;
+
+ u->mixer_dsp_fd = -1;
+
+ if (ioctl (u->mixer_fd, SNDCTL_SYSINFO, &si) < 0) {
+ pa_log_debug («SNDCTL_SYSINFO failed»);
+ goto fail;
+ }
+ for (i = 0; i < si.nummixers; i++) { + mi.dev = i; + if (ioctl (u->mixer_fd, SNDCTL_MIXERINFO, &mi) < 0) {
+ pa_log_debug(«SNDCTL_MIXERINFO failed»);
+ goto fail;
+ }
+ if (mi.enabled != 0) {
+ /*
+ * There could be multiple mixers. First we only care about
+ * ones which are enabled. In any case we should not touch
+ * disabled mixers! But beyond that it may not be clear which
+ * one to use! There is a way to relate the card number to the
+ * device node name. But there does not seem to be a real good
+ * way to chose which one to use. So maybe an env. var. could
+ * be used to select a dsp device node name and then pick the
+ * correct mixer number. (See load_devices() in audioctl).
+ * This code now will always pick the first enabled mixer
+ * found. Which may be wrong for multiple mixers and/or sound
+ * cards. It may be possible/desirable to control all mixers
+ * found at the same time???
+ */
+ break;
+ }
+ }
+
+ if (i < si.nummixers) {
+ struct stat sbuf;
+
+ if ((stat(mi.devnode, &sbuf) != 0) ||
+ ((sbuf.st_mode & S_IFCHR) == 0)) {
+ pa_log(«Failed to get mixer dsp device.»);
+ i = si.nummixers;
+ }
+ }
+
+ if (i < si.nummixers && + (u->mixer_dsp_fd = pa_oss_open_mixer(mi.devnode)) >= 0) {
+
+ /* Will cause for loop to exit if not filled in by OSS */
+ u->mixer_cmax = -1;
+ if (ioctl(u->mixer_dsp_fd, SNDCTL_MIX_NREXT, &u->mixer_cmax) < 0) { + pa_log(«Failed to get max control.»); + goto fail; + } + + pa_log_debug («Opened mixer device %d with %d controls\n», + mi.dev, mi.nrext); + + u->mixer_sink_control = -1;
+ u->mixer_source_control = -1;
+
+ for (i=0; i < u->mixer_cmax; i++) {
+ memset (&(u->sink_mixext), 0, sizeof (oss_mixext));
+
+#ifdef IGNORE_DEV
+ /* This will cause dev to be ignored */
+ u->sink_mixext.dev = -1;
+#else
+ u->sink_mixext.dev = mi.dev;
+#endif
+
+ /*
+ * The real way to pick a control on a mixer is with this
+ * number. Note that control numbers are unique across all
+ * mixers. So dev can just be ignored. When dev is included
+ * it will only be used to check for correct dev from
+ * userland. But it will not be used to select a mixer.
+ */
+ u->sink_mixext.ctrl = i;
+
+ pa_log_debug («Control %d», u->sink_mixext.ctrl);
+
+ if (ioctl (u->mixer_dsp_fd, SNDCTL_MIX_EXTINFO,
+ &(u->sink_mixext)) < 0) { + pa_log_debug («SNDCTL_MIX_EXTINFO failed»); + continue; + } + + pa_log_debug (» name : %s», u->sink_mixext.extname);
+ pa_log_debug (» type : %s (%d)»,
+ mixer_ext_type_get_name (u->sink_mixext.type),
+ u->sink_mixext.type);
+ pa_log_debug (» maxval : %d», u->sink_mixext.maxvalue);
+ pa_log_debug (» parent : %d», u->sink_mixext.parent);
+ mixer_showflags (u->sink_mixext.flags);
+
+ if ((u->sink_mixext.flags & MIXF_PCMVOL)) {
+ pa_log_debug («First PCM control: %d», i);
+ u->mixer_sink_control = i;
+ break;
+ }
+
+ /*
+ * Note that MIXF_MAINVOL may not be an exclusive single
+ * control. For example on AudioHD there will be one for each
+ * output jack (Green, Black, Orange…). So to really do a
+ * master volume you would need to do all MIXF_MAINVOL at the
+ * same time…
+ */
+ if (((u->sink_mixext.flags & MIXF_MAINVOL)) &&
+ u->mixer_sink_control == -1) {
+ pa_log_debug («First main volume control: %d», i);
+ u->mixer_sink_control = i;
+ }
+ }
+
+ if (u->mixer_sink_control != -1) {
+ pa_log_debug («Setting OSS sink callbacks.»);
+ pa_sink_set_get_volume_callback(u->sink, sink_get_volume);
+ pa_sink_set_set_volume_callback(u->sink, sink_set_volume);
+ u->sink->n_volume_steps = 101;
+ do_close = FALSE;
+ } else {
+ pa_log_debug («Not setting OSS sink callbacks.»);
+ }
+
+ for (i=0; i < mi.nrext; i++) { + memset (&(u->source_mixext), 0, sizeof (oss_mixext));
+#ifdef IGNORE_DEV
+ /* This will cause dev to be ignored */
+ u->source_mixext.dev = -1;
+#else
+ u->source_mixext.dev = mi.dev;
+#endif
+ /*
+ * The real way to pick a control on a mixer is with this
+ * number. Note that control numbers are unique across all
+ * mixers. So dev can just be ignored. When dev is included
+ * it will only be used to check for correct dev from userland.
+ * But it will not be used to select a mixer.
+ */
+ u->source_mixext.ctrl = i;
+
+ pa_log_debug («Control %d», u->source_mixext.ctrl);
+
+ if (ioctl (u->mixer_dsp_fd, SNDCTL_MIX_EXTINFO,
+ &(u->source_mixext)) == -1) {
+ pa_log_debug («SNDCTL_MIX_EXTINFO failed»);
+ continue;
+ }
+
+ pa_log_debug (» name : %s», u->source_mixext.extname);
+ pa_log_debug (» type : %s (%d)»,
+ mixer_ext_type_get_name (u->source_mixext.type),
+ u->source_mixext.type);
+ pa_log_debug (» maxval : %d», u->source_mixext.maxvalue);
+ pa_log_debug (» parent : %d», u->source_mixext.parent);
+ mixer_showflags (u->source_mixext.flags);
+
+ /*
+ * There may be more then one MIXF_RECVOL on a mixer. In fact
+ * for audioHD the can be three (line-in, mix-in, and cd-in).
+ * For a master gain it may be good to adjust all…
+ */
+ if ((u->source_mixext.flags & MIXF_RECVOL)) {
+ pa_log_debug («First REC control: %d», i);
+ u->mixer_source_control = i;
+ break;
+ }
+ }
+
+ if (u->mixer_source_control != -1) {
+ pa_log_debug («Setting OSS source callbacks.»);
+ pa_source_set_get_volume_callback(u->source, source_get_volume);
+ pa_source_set_set_volume_callback(u->source, source_set_volume);
+ u->source->n_volume_steps = 101;
+ do_close = FALSE;
+ } else {
+ pa_log_debug («Not setting OSS source callbacks.»);
+ }
+
+ if (do_close == TRUE) {
+ pa_close(u->mixer_dsp_fd);
+ u->mixer_dsp_fd = -1;
+ }
+ }
+
+#else
if (ioctl(fd, SOUND_MIXER_READ_DEVMASK, &u->mixer_devmask) < 0) pa_log_warn(«SOUND_MIXER_READ_DEVMASK failed: %s», pa_cstrerror(errno)); else { @@ -1445,11 +1810,14 @@ int pa__init(pa_module*m) { do_close = false; } } +#endif if (do_close) { pa_close(u->mixer_fd);
u->mixer_fd = -1;
+#ifndef HAVE_OSSV4
u->mixer_devmask = 0;
+#endif
}
}

@@ -1568,6 +1936,10 @@ void pa__done(pa_module*m) {
if (u->fd >= 0)
pa_close(u->fd);

+#ifdef HAVE_OSSV4
+ if (u->mixer_dsp_fd >= 0)
+ pa_close(u->mixer_dsp_fd);
+#endif
if (u->mixer_fd >= 0)
pa_close(u->mixer_fd);

diff -rupN pulseaudio-5.99.3.old/src/modules/oss/oss-util.c pulseaudio-5.99.3/src/modules/oss/oss-util.c
— pulseaudio-5.99.3.old/src/modules/oss/oss-util.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/oss/oss-util.c 2015-02-08 22:11:11.581982216 +0200
@@ -246,6 +246,190 @@ int pa_oss_set_fragments(int fd, int nfr
return 0;
}

+#ifdef HAVE_OSSV4
+static int
+oss4_mixer_slider_pack_volume (oss_mixext *mixext, int channels, const pa_cvolume *volume)
+{
+ int val = 0;
+ int lvol = 0;
+ int rvol = 0;
+ int lval = 0;
+ int rval = 0;
+
+ switch (mixext->type) {
+ case MIXT_MONOSLIDER:
+ case MIXT_MONOSLIDER16:
+ case MIXT_SLIDER:
+ lvol = volume->values[0] > PA_VOLUME_NORM ? PA_VOLUME_NORM : volume->values[0];
+ val = (lvol*mixext->maxvalue)/PA_VOLUME_NORM;
+ break;
+
+ case MIXT_STEREOSLIDER:
+ lvol = volume->values[0] > PA_VOLUME_NORM ? PA_VOLUME_NORM : volume->values[0];
+ lval = (lvol*mixext->maxvalue)/PA_VOLUME_NORM;
+ if (channels >= 2) {
+ rvol = volume->values[1] > PA_VOLUME_NORM ? PA_VOLUME_NORM : volume->values[1];
+ rval = (rvol*mixext->maxvalue)/PA_VOLUME_NORM;
+ }
+
+ val = ((rval & 0xff) << 8) | (lval & 0xff); + break; + + case MIXT_STEREOSLIDER16: + lvol = volume->values[0] > PA_VOLUME_NORM ? PA_VOLUME_NORM : volume->values[0];
+ lval = (lvol*mixext->maxvalue)/PA_VOLUME_NORM;
+ if (channels >= 2) {
+ rvol = volume->values[1] > PA_VOLUME_NORM ? PA_VOLUME_NORM : volume->values[1];
+ rval = (rvol*mixext->maxvalue)/PA_VOLUME_NORM;
+ }
+
+ val = ((rval & 0xffff) << 16) | (lval & 0xffff); + + break; + + default: + return 0; + } + + return val; +} + +static void +oss4_mixer_slider_unpack_volume (oss_mixext *mixext, int v, pa_cvolume * volume) +{ + uint32_t val, vol; + + val = (uint32_t) v; + switch (mixext->type) {
+ case MIXT_SLIDER:
+ vol = val;
+ volume->values[0] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ if (volume->channels >= 2) {
+ volume->values[1] = volume->values[0];
+ }
+ break;
+ case MIXT_MONOSLIDER:
+ /* oss repeats the value in the upper bits, as if it was stereo */
+ vol = val & 0x00ff;
+ volume->values[0] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ if (volume->channels >= 2) {
+ volume->values[1] = volume->values[0];
+ }
+ break;
+ case MIXT_MONOSLIDER16:
+ /* oss repeats the value in the upper bits, as if it was stereo */
+ vol = val & 0x0000ffff;
+ volume->values[0] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ if (volume->channels >= 2) {
+ volume->values[1] = volume->values[0];
+ }
+ break;
+ case MIXT_STEREOSLIDER:
+ vol = (val & 0x00ff);
+ volume->values[0] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ if (volume->channels >= 2) {
+ vol = (val & 0xff00) >> 8;
+ volume->values[1] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ }
+ break;
+ case MIXT_STEREOSLIDER16:
+ vol = (val & 0x0000ffff);
+ volume->values[0] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ if (volume->channels >= 2) {
+ vol = (val & 0xffff0000) >> 16;
+ volume->values[1] = PA_CLAMP_VOLUME((vol * PA_VOLUME_NORM) / mixext->maxvalue);
+ }
+ break;
+ default:
+ return;
+ }
+}
+
+static int
+oss4_mixer_get_control_val (int fd, oss_mixext *mixext, int *val)
+{
+ oss_mixer_value ossval = { 0, };
+
+ /* ossval.dev = mixext->dev; */
+ ossval.dev = -1; /* if -1 on entry then is ignored */
+ /*
+ * The real way to pick a control on a mixer is with this number.
+ * Note that control numbers are uniq across all mixers. So dev
+ * can just be ignored. When dev is included it will only be used
+ * to check for correct dev from userland. But it will not be used
+ * to select a mixer.
+ */
+ ossval.ctrl = mixext->ctrl;
+ ossval.timestamp = mixext->timestamp;
+
+ if (ioctl (fd, SNDCTL_MIX_READ, &ossval) == -1) {
+ pa_log_debug («SNDCTL_MIX_READ failed»);
+ *val = 0;
+ return -1;
+ }
+
+ *val = ossval.value;
+ pa_log_debug («got value 0x%08x from %s», *val, mixext->extname);
+ return 0;
+}
+
+static int
+oss4_mixer_set_control_val (int fd, oss_mixext *mixext, int val)
+{
+ oss_mixer_value ossval = { 0, };
+
+ /* ossval.dev = mixext->dev; */
+ ossval.dev = -1; /* if -1 on entry then is ignored */
+ /*
+ * The real way to pick a control on a mixer is with this number.
+ * Note that control numbers are uniq across all mixers. So dev
+ * can just be ignored. When dev is included it will only be used
+ * to check for correct dev from userland. But it will not be used
+ * to select a mixer.
+ */
+ ossval.ctrl = mixext->ctrl;
+ ossval.timestamp = mixext->timestamp;
+ ossval.value = val;
+
+ if (ioctl (fd, SNDCTL_MIX_WRITE, &ossval) == -1) {
+ pa_log_debug («SNDCTL_MIX_WRITE failed»);
+ return -1;
+ }
+
+ pa_log_debug («set value 0x%08x on %s», val, mixext->extname);
+ return 0;
+}
+
+int pa_oss_get_volume(int fd, oss_mixext *mixext, const pa_sample_spec *ss, pa_cvolume *volume) {
+ int v = 0;
+
+ if (oss4_mixer_get_control_val (fd, mixext, &v) != 0) {
+ pa_log_debug («Getting volume failed»);
+ return -1;
+ }
+
+ pa_cvolume_reset(volume, ss->channels);
+
+ oss4_mixer_slider_unpack_volume (mixext, v, volume);
+
+ return 0;
+}
+
+int pa_oss_set_volume(int fd, oss_mixext *mixext, const pa_sample_spec *ss, const pa_cvolume *volume) {
+ int val = 0;
+
+ val = oss4_mixer_slider_pack_volume (mixext, ss->channels, volume);
+
+ if (oss4_mixer_set_control_val (fd, mixext, val) != 0) {
+ pa_log_debug («Setting volume failed»);
+ return -1;
+ }
+
+ return 0;
+}
+
+#else
+
int pa_oss_get_volume(int fd, unsigned long mixer, const pa_sample_spec *ss, pa_cvolume *volume) {
char cv[PA_CVOLUME_SNPRINT_VERBOSE_MAX];
unsigned vol;
@@ -288,6 +472,7 @@ int pa_oss_set_volume(int fd, unsigned l
pa_log_debug(«Wrote mixer settings: %s», pa_cvolume_snprint(cv, sizeof(cv), volume));
return 0;
}
+#endif

static int get_device_number(const char *dev) {
const char *p, *e;
@@ -386,9 +571,11 @@ int pa_oss_get_hw_description(const char
return r;
}

-static int open_mixer(const char *mixer) {
+int pa_oss_open_mixer(const char *mixer) {
int fd;

+ pa_log_debug («Opening device %s», mixer);
+
if ((fd = pa_open_cloexec(mixer, O_RDWR|O_NDELAY, 0)) >= 0)
return fd;

@@ -400,19 +587,22 @@ int pa_oss_open_mixer_for_device(const c
char *fn;
int fd;

– if ((n = get_device_number(device)) < 0)
+ if ((n = get_device_number(device)) < 0) { + pa_log_debug («Cannot find device»); return -1; + } if (n == 0) – if ((fd = open_mixer(«/dev/mixer»)) >= 0)
+ if ((fd = pa_oss_open_mixer(«/dev/mixer»)) >= 0)
return fd;

fn = pa_sprintf_malloc(«/dev/mixer%i», n);
– fd = open_mixer(fn);
+ fd = pa_oss_open_mixer(fn);
pa_xfree(fn);

if (fd < 0)
pa_log_warn(«Failed to open mixer ‘%s’: %s», device, pa_cstrerror(errno));
+ else

return fd;
}
diff -rupN pulseaudio-5.99.3.old/src/modules/oss/oss-util.h pulseaudio-5.99.3/src/modules/oss/oss-util.h
— pulseaudio-5.99.3.old/src/modules/oss/oss-util.h 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/modules/oss/oss-util.h 2015-02-08 22:11:11.582249622 +0200
@@ -29,11 +29,21 @@ int pa_oss_auto_format(int fd, pa_sample

int pa_oss_set_fragments(int fd, int frags, int frag_size);

+#define HAVE_OSSV4
+
+#ifdef HAVE_OSSV4
+int pa_oss_set_volume(int fd, oss_mixext *mixext, const pa_sample_spec *ss, const pa_cvolume *volume);
+int pa_oss_get_volume(int fd, oss_mixext *mixext, const pa_sample_spec *ss, pa_cvolume *volume);
+
+#else
+
int pa_oss_set_volume(int fd, unsigned long mixer, const pa_sample_spec *ss, const pa_cvolume *volume);
int pa_oss_get_volume(int fd, unsigned long mixer, const pa_sample_spec *ss, pa_cvolume *volume);
+#endif

int pa_oss_get_hw_description(const char *dev, char *name, size_t l);

int pa_oss_open_mixer_for_device(const char *device);
+int pa_oss_open_mixer(const char *device);

#endif
diff -rupN pulseaudio-5.99.3.old/src/pulse/sample.h pulseaudio-5.99.3/src/pulse/sample.h
— pulseaudio-5.99.3.old/src/pulse/sample.h 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/pulse/sample.h 2015-02-08 22:11:11.582624201 +0200
@@ -121,7 +121,9 @@ PA_C_DECL_BEGIN
#if defined(__sparc__) && defined(_BIG_ENDIAN)
#define WORDS_BIGENDIAN
#endif

+#if defined(_BIG_ENDIAN)
+#define WORDS_BIGENDIAN
+#endif
#endif

/** Maximum number of allowed channels */
diff -rupN pulseaudio-5.99.3.old/src/pulsecore/core-scache.h pulseaudio-5.99.3/src/pulsecore/core-scache.h
— pulseaudio-5.99.3.old/src/pulsecore/core-scache.h 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/pulsecore/core-scache.h 2015-02-08 22:11:11.582922144 +0200
@@ -25,7 +25,6 @@
#include <pulsecore/memchunk.h> #include <pulsecore/sink.h>

-#define PA_SCACHE_ENTRY_SIZE_MAX (1024*1024*16)

typedef struct pa_scache_entry {
uint32_t index;
@@ -65,4 +64,5 @@ size_t pa_scache_total_size(pa_core *c);

void pa_scache_unload_unused(pa_core *c);

+#define PA_SCACHE_ENTRY_SIZE_MAX (1024*1024*16)
#endif
diff -rupN pulseaudio-5.99.3.old/src/pulsecore/shm.c pulseaudio-5.99.3/src/pulsecore/shm.c
— pulseaudio-5.99.3.old/src/pulsecore/shm.c 2015-01-21 16:16:53.000000000 +0200
+++ pulseaudio-5.99.3/src/pulsecore/shm.c 2015-02-08 22:11:11.583260666 +0200
@@ -371,8 +371,11 @@ int pa_shm_cleanup(void) {
if (strncmp(de->d_name, «pulse-shm-«, SHM_ID_LEN))
#endif
continue;

+#if defined(__sun)
+ if (pa_atou(de->d_name + 10, &id) < 0) +#else if (pa_atou(de->d_name + SHM_ID_LEN, &id) < 0)
+#endif
continue;

if (pa_shm_attach(&seg, id, false) < 0) diff -rupN pulseaudio-5.99.3.old/src/utils/padsp.c pulseaudio-5.99.3/src/utils/padsp.c — pulseaudio-5.99.3.old/src/utils/padsp.c 2015-01-21 16:16:53.000000000 +0200 +++ pulseaudio-5.99.3/src/utils/padsp.c 2015-02-08 22:17:07.921244432 +0200 @@ -2275,6 +2275,7 @@ static int dsp_ioctl(fd_info *i, unsigne break; } +#ifndef __sun case SOUND_PCM_READ_RATE: debug(DEBUG_LEVEL_NORMAL, __FILE__»: SOUND_PCM_READ_RATE\n»); @@ -2298,6 +2299,7 @@ static int dsp_ioctl(fd_info *i, unsigne *(int*) argp = pa_sample_size(&i->sample_spec)*8;
pa_threaded_mainloop_unlock(i->mainloop);
break;
+#endif

case SNDCTL_DSP_GETOPTR: {
count_info *info;
@@ -2368,7 +2370,7 @@ fail:
return ret;
}

-#ifdef sun
+#ifdef __sun
int ioctl(int fd, int request, …) {
#else
int ioctl(int fd, unsigned long request, …) {

Follow

Ενημερωθείτε για κάθε νέα δημοσίευση στο email σας.