SOUND freq, duration

DOS specific questions.
RadSurfer
Posts: 10
Joined: Jan 13, 2006 2:07
Contact:

SOUND freq, duration

Post by RadSurfer »

Anyone know of a good way to implement the SOUND statement in
FB-32 ? Surprising this isn't here; I'm sure this could be easily done.

I was thinking of some kind of OPL3/FM chip programming, easy to
do with nice versatile ISA cards...
PCI sounds card are a little trickier to access....

Surely there must be some open-source Sound routines appropriate
for FB-32.
Also, a PLAY command would be nice, but not as essential as the
actual SOUND statement itself.

Any comments?

//RadSurfer//
DOS386
Posts: 798
Joined: Jul 02, 2005 20:55

Sound in DOS

Post by DOS386 »

Known problem.

http://www.freebasic.net/forum/viewtopic.php?t=2171

http://www.freebasic.net/wiki/wikka.php ... ompilerFAQ

Sound in DOS is definitely doable, but unfortunately not trivial.

Nevertheless, a SOUND command using the "archaic" speaker, would
be easy to implement and nice.

Beware: this speaker can be used even to play music, MP3 & WAV files:

http://advsys.net/ken/utils.htm

KPC.EXE 33,559 bytes Plays WAV or VOC files through the PC speaker.

MP3PC.EXE 70,021 bytes Got no sound card? MP3PC plays MP3 files through your PC speaker! For some reason I like to make programs work through the PC speaker. Some people still don't know that it's possible to play real sounds through it.
yetifoot
Posts: 1710
Joined: Sep 11, 2005 7:08
Location: England
Contact:

Post by yetifoot »

As a aside here is another good prog for DOS that plays divx, mpeg4 etc video

http://www.multimediaware.com/qv/index.html
yetifoot
Posts: 1710
Joined: Sep 11, 2005 7:08
Location: England
Contact:

Post by yetifoot »

heres some code that plays a frequency in DOS/Lin/Win via the PC Speaker, This code also works on windows >= NT, without admin status, because in that case it uses Beep from the API rather than direct port access.

On linux, i believe when I tested this, I may have been logged in as root (silly, i know), so am unsure if port access is allowed in normal user mode.

IMPORTANT:

The forum code blocks make some of the asm uppercase, like out becomes Out, and or becomes Or You will have to adjust these lines for the code to compile.

EDIT : 23rd July 2006. Fixed for 0.16/0.17

Code: Select all

' Sound Function v0.3 For DOS/Linux/Win by yetifoot
'
' Tested on:
'    Slackware 10.2
'    Win98
'    WinXP
'    DOS
'
' Credits:
'    http://www.frontiernet.net/~fys/snd.htm
'    http://delphi.about.com/cs/adptips2003/a/bltip0303_3.htm
'
' Notes:
'    On windows >= NT, direct port access is not allowed, in this instance
'    however we can use the WinAPI Beep function, which allows freq and duration
'    

'        Octave 0    1    2    3    4    5    6    7
'        Note
'        C     16   33   65  131  262  523 1046 2093
'        C#    17   35   69  139  277  554 1109 2217
'        D     18   37   73  147  294  587 1175 2349
'        D#    19   39   78  155  311  622 1244 2489
'        E     21   41   82  165  330  659 1328 2637
'        F     22   44   87  175  349  698 1397 2794
'        F#    23   46   92  185  370  740 1480 2960
'        G     24   49   98  196  392  784 1568 3136
'        G#    26   52  104  208  415  831 1661 3322
'        A     27   55  110  220  440  880 1760 3520
'        A#    29   58  116  233  466  932 1865 3729
'        B     31   62  123  245  494  988 1975 3951

#ifdef __FB_WIN32__ 
  #include once "windows.bi"
#endif

Sub Sound_DOS_LIN(Byval freq As Uinteger, dur As Uinteger)
  Dim t As Double
  Dim fixed_freq As uShort
  
    fixed_freq = 1193181 \ freq
    
    ASM
      mov  dx, &H61                  ' turn speaker on
      in   al, dx
      or   al, &H03
      out  dx, al
      mov  dx, &H43                  ' get the timer ready
      mov  al, &HB6
      out  dx, al
      mov  ax, word ptr [fixed_freq] ' move freq to ax
      mov  dx, &H42                  ' port to out
      out  dx, al                    ' out low order
      xchg ah, al                   
      out  dx, al                    ' out high order
    End ASM
    
    t = Timer
    While ((Timer - t) * 1000) < dur ' wait for out specified duration
      Sleep(1)
    Wend
    
    ASM
      mov  dx, &H61                  ' turn speaker off
      in   al, dx
      and  al, &HFC
      out  dx, al
    End ASM
    
End Sub

Sub Sound(Byval freq As Uinteger, dur As Uinteger)
  #ifndef __FB_WIN32__
    ' If not windows Then call the asm version.
    Sound_DOS_LIN(freq, dur)
  #else
    ' If Windows
    Dim osv As OSVERSIONINFO
    
      osv.dwOSVersionInfoSize = sizeof(OSVERSIONINFO)
      GetVersionEx(@osv)
      
      Select Case osv.dwPlatformId
        Case VER_PLATFORM_WIN32_NT       
          ' If NT then use Beep from API
          Beep_(freq, dur)
        Case Else
          ' If not on NT then use the same as DOS/Linux
          Sound_DOS_LIN(freq, dur)
      End Select
  #endif
End Sub

' TEST

Sound(523, 60)  'C5
Sound(587, 60)  'D5
Sound(659, 60)  'E5
Sound(698, 60)  'F5
Sound(784, 60)  'G5
Sound(880, 60)  'A5
Sound(988, 60)  'B5
Sound(1046, 60) 'C6
Last edited by yetifoot on Jul 23, 2006 2:35, edited 1 time in total.
yetifoot
Posts: 1710
Joined: Sep 11, 2005 7:08
Location: England
Contact:

Post by yetifoot »

updated to be win/dos/linux compatible.
Antoni
Posts: 1393
Joined: May 27, 2005 15:40
Location: Barcelona, Spain

Post by Antoni »

Hey, that's great!
It squeaks as an old vingage 86' XT !! :D

It works in Windows 2000 SP4

EDITED:
I played a little with it, here is a "Pure FB version"

Code: Select all

'speakersound.bas  
Sub Sound(ByVal freq As uInteger, dur As uInteger)
  Dim t As Double,f1 as unsigned short
    f1 = 1193181 \ freq
    out &h61,inp(&h61) or 3
    out &h43,&hb6
    out &h42,lobyte(f1) 
    out &h42,hibyte(f1)
    t=timer  
    While ((Timer - t) * 1000) < dur
      sleep 0,1
    Wend
    out &h61,inp(&h61) and &hfc
end sub

  
Sound(523, 60)  'C5
Sound(587, 60)  'D5
Sound(659, 60)  'E5
Sound(698, 60)  'F5
Sound(784, 60)  'G5
Sound(880, 60)  'A5
Sound(988, 60)  'B5
Sound(1046, 60) 'C6 

It works in Windows provided you have Admin rights...
yetifoot
Posts: 1710
Joined: Sep 11, 2005 7:08
Location: England
Contact:

Post by yetifoot »

Very nice work Antoni. I tested using 0.15 on DOS, WinXP, and Slackware 10.2 and it works fine. Only one left to test is Win9x, but i'm guessing that will be fine.
RadSurfer
Posts: 10
Joined: Jan 13, 2006 2:07
Contact:

Standard Sound Command

Post by RadSurfer »

If only other tasks could be done while the PC
Speaker is kept busy...

I never did understand why Sound Blaster Live
doesn't provide DOS level access any more with some
of their models. Very very foolish. And trying Dos-drivers
from other models does not seem to work, which further
makes them foolish.

If you have a P2 or 1st generation Pentium 3 with ISA slots,
it is possible to access the OPL-3/Midi FM chip. Advantages are
it doesn't tie up the system. I'm sure its possible at PCI level
is you're good with that sort of low-level device drivers.
Antoni wrote:Hey, that's great!
It squeaks as an old vingage 86' XT !! :D

It works in Windows 2000 SP4

EDITED:
I played a little with it, here is a "Pure FB version"
<snip>
Sound(523, 60) 'C5
Sound(587, 60) 'D5
Sound(659, 60) 'E5
Sound(698, 60) 'F5
Sound(784, 60) 'G5
Sound(880, 60) 'A5
Sound(988, 60) 'B5
Sound(1046, 60) 'C6
DrV
Site Admin
Posts: 2116
Joined: May 27, 2005 18:39
Location: Midwestern USA
Contact:

Post by DrV »

You can get DOS SB Live drivers here: http://easymamecab.mameworld.net/html/snddosdr.htm I've used them with success with an integrated SBPCI 128.
opicard
Posts: 81
Joined: Feb 26, 2008 16:40

controling sound level

Post by opicard »

Yes it works fine except sound level.

Please Is there any news since 2006 about it ?
TESLACOIL
Posts: 1769
Joined: Jun 20, 2010 16:04
Location: UK
Contact:

sweet

Post by TESLACOIL »

sweet , ive realy missed the retro pc sound

works on xp sp3

i added pc speaker to volume control panel , but volume or mute have no effect. i can still hear the sound regardless


for i =1 to 1200 step 7:Sound(i, 4): next ' light saber ?

sleep

for i =100 to 800 step 2.3:Sound(i, 3): next
opicard
Posts: 81
Joined: Feb 26, 2008 16:40

Re: sweet

Post by opicard »

TESLACOIL wrote:sweet , ive realy missed the retro pc sound

works on xp sp3

i added pc speaker to volume control panel , but volume or mute have no effect. i can still hear the sound regardless


for i =1 to 1200 step 7:Sound(i, 4): next ' light saber ?

sleep

for i =100 to 800 step 2.3:Sound(i, 3): next


so no way to get volume control?
darkhog
Posts: 132
Joined: Oct 05, 2011 21:19

Post by darkhog »

This code:

Code: Select all

' Sound Function v0.3 For DOS/Linux/Win by yetifoot
'
' Tested on:
'    Slackware 10.2
'    Win98
'    WinXP
'    DOS
'
' Credits:
'    http://www.frontiernet.net/~fys/snd.htm
'    http://delphi.about.com/cs/adptips2003/a/bltip0303_3.htm
'
' Notes:
'    On windows >= NT, direct port access is not allowed, in this instance
'    however we can use the WinAPI Beep function, which allows freq and duration
'   

'        Octave 0    1    2    3    4    5    6    7
'        Note
'        C     16   33   65  131  262  523 1046 2093
'        C#    17   35   69  139  277  554 1109 2217
'        D     18   37   73  147  294  587 1175 2349
'        D#    19   39   78  155  311  622 1244 2489
'        E     21   41   82  165  330  659 1328 2637
'        F     22   44   87  175  349  698 1397 2794
'        F#    23   46   92  185  370  740 1480 2960
'        G     24   49   98  196  392  784 1568 3136
'        G#    26   52  104  208  415  831 1661 3322
'        A     27   55  110  220  440  880 1760 3520
'        A#    29   58  116  233  466  932 1865 3729
'        B     31   62  123  245  494  988 1975 3951

#ifdef __FB_WIN32__
  #include once "windows.bi"
#endif

Sub Sound_DOS_LIN(Byval freq As Uinteger, dur As Uinteger)
  Dim t As Double
  Dim fixed_freq As uShort
 
    fixed_freq = 1193181 \ freq
   
    ASM
      mov  dx, &H61                  ' turn speaker on
      in   al, dx
      or   al, &H03
      out  dx, al
      mov  dx, &H43                  ' get the timer ready
      mov  al, &HB6
      out  dx, al
      mov  ax, word ptr [fixed_freq] ' move freq to ax
      mov  dx, &H42                  ' port to out
      out  dx, al                    ' out low order
      xchg ah, al                   
      out  dx, al                    ' out high order
    End ASM
   
    t = Timer
    While ((Timer - t) * 1000) < dur ' wait for out specified duration
      Sleep(1)
    Wend
   
    ASM
      mov  dx, &H61                  ' turn speaker off
      in   al, dx
      and  al, &HFC
      out  dx, al
    End ASM
   
End Sub

Sub Sound(Byval freq As Uinteger, dur As Uinteger)
  #ifndef __FB_WIN32__
    ' If not windows Then call the asm version.
    Sound_DOS_LIN(freq, dur)
  #else
    ' If Windows
    Dim osv As OSVERSIONINFO
   
      osv.dwOSVersionInfoSize = sizeof(OSVERSIONINFO)
      GetVersionEx(@osv)
     
      Select Case osv.dwPlatformId
        Case VER_PLATFORM_WIN32_NT       
          ' If NT then use Beep from API
          Beep_(freq, dur)
        Case Else
          ' If not on NT then use the same as DOS/Linux
          Sound_DOS_LIN(freq, dur)
      End Select
  #endif
End Sub

' TEST

Sound(523, 60)  'C5
Sound(587, 60)  'D5
Sound(659, 60)  'E5
Sound(698, 60)  'F5
Sound(784, 60)  'G5
Sound(880, 60)  'A5
Sound(988, 60)  'B5
Sound(1046, 60) 'C6
doesn't work. It exits with runtime error 139 and memory protection violation. Ran on opensuse 11.3 with normal user rights. Kernel is 2.6.34-12-desktop.

//edit: Tried Antoni's code. While it didn't have any access violation things, sound wasn't playing via PC speaker either.
Mihail_B
Posts: 273
Joined: Jan 29, 2008 11:20
Location: Romania
Contact:

Post by Mihail_B »

darkhog wrote:This code:
....(code)....
doesn't work. It exits with runtime error 139 and memory protection violation. Ran on opensuse 11.3 with normal user rights. Kernel is 2.6.34-12-desktop.
//edit: Tried Antoni's code. While it didn't have any access violation things, sound wasn't playing via PC speaker either.
yes it should not work . it's ok 'till now .
:)
did I scared you ? i hope not !

before you can access io ports in linux, you need get permission to access them .

to do that use : [ioperm()] see http://linux.die.net/man/2/ioperm for ioperm info ... (and also http://www.freebasic.net/forum/viewtopi ... ght=ioperm)

so you need to say something like this :

#ifdef __FB_LINUX__
#include "sys/io.bi"
iopl(4) //IOPL priviledge level but 4=0 !!!
ioperm(my_port,num_bytes,1)

'ioperm(start,count,enabled or disabled) ' In TSS -> i/o permission bitmap, enable =1, disable=0, also virtualization -> request goes through linux drivers)


---and then do your port stuff ---
Note for each new port you are trying to access you need to get permission with io port (you need to be root also or a part of an admin group)
....

so concludiong :
study :
- iopl(4)
and
- ioperm(start,count,enabled vs. disabled)

good luck !
opicard
Posts: 81
Joined: Feb 26, 2008 16:40

Re: SOUND freq, duration

Post by opicard »

Somebody could teach me why this sound freq works properly with a core I2 and not with a coreI5 intel processor?
Post Reply