C++Guns – RoboBlog blogging the bot

28.08.2016

Stellpult Fortschritt

Filed under: Allgemein — Tags: , , — Thomas @ 19:08

Hier der Fortschritt des Stellpultes.
Der Gleisverlauf muss nochmal nachgezogen werden, ist schlecht zu erkennen.
Die Messinstrumente für Spannung/Strom für die Hauptstrecke und Bergbahn sind montiert und angeschlossen.
Dazwischen diverse Bedienfunktionen und zwei Drehschalter für die Bremsgleise vor dem Hbf. Rechts daneben die Steuerung der Lichtstromkreise.

Stellpult_2

Ansicht bei Dunkelheit. Schön zu sehen ist die Stellung der sechs Signale und drei Weichen, die bisher an die Stellpult Elektronik angeschlossen sind. Oben die vier Kontrollleuchten der Traffos und links die Traffos selbst.

Stellpult_1

Ansicht von unten. Man wundert sich doch über die Menge der Kabel für die paar Taster. Rechts das Klemmfeld.

Stellpult_3

Hier ist ein Teil der Steuerung zu sehen. Der Rest muss erst noch gelötet werden.
Die erste Platine rechts unten sind die Taster Umschalter für Hand/Automatik Steuerung. Dahinter mit gelbem Aufkleber neuen Flipflops mit Verriegelung. Danach kommen noch zwei Monoflop Platinen a 9 Flops. Da jede Weiche eben zwei Spulen hat, braucht es für neu Flipflops eben 18 Monoflops.
An der Rückwand angebracht ist der Traffo mit Sicherungen, 12V 4A. Links danaben zwei mal zwei Gleichrichter für die Strom und Spannungsanzeige. Auch wenn die Messgeräte selbst für Gleichspannung ausgelegt sind, fährt unsere Bahn mit Wechselspannung.

Stellpult_4

Gesamtansicht des Stellwerkes. Es ist noch genügend Platz für weitere Platinen und rollendes Material. Der schwarze Kasten ist die Steuerung der Pendelzugstrecke. Allerdings nicht in Relais, sondern in IC Technik.

Stellpult_5

20.08.2016

Kaffeeecke

Filed under: Allgemein — Thomas @ 18:08
Alt

Alt

Situation davor. Der Schrank mit den Doppeltüren kommt weg. Die Microwelle rutscht rüber.

IMG_6592_1

So kommt man besser an Theromix und Wasserx dran ohne sich die Birne anzuschlagen. Und es ist endlich mal Platz für ein Handtuch! Die Schiene muss ich noch mit einem Kabelkanal o.ä. verdecken.

Kaffeeecke fast fertig

Kaffeeecke fast fertig

Kaffeeecke fast fertig. Unter und Oberschrank mit Arbeitsplatte sind neu. Nun steht der Trockner nicht so alleine herum. Neue Mülleimer und Kaffee finden auch ihren Platz.

IMG_6593_1

Es fehlen noch Randleisten, Steckdosen, Arbeitsplatz Beleuchtung und eine Blende für den Trockner. Aber da muss ich mir erst über die Abluft Sorgen machen, sonst trocknet es ja nicht.

19.08.2016

Best C++ GC ever!

Filed under: Allgemein — Tags: — Thomas @ 11:08

template< typename T>
T* makeObject() {
  static T* obj = nullptr;
  delete obj;
  obj = new T();
  return obj;
}

26.06.2016

malloc info fortran

Filed under: Allgemein — Tags: — Thomas @ 00:06

Code snipped to get detailed information about memory usage

mallocinfo.f95.zip

Related: Code snipped to read /proc status with fortran.


module MallocInfo_m
  use :: iso_c_binding
  implicit none
  
    !> This structure type is used to return information about the dynamic memory allocator.
    type, bind(c) :: MallInfo_t
      !> This is the total size of memory allocated with sbrk by malloc, in bytes.
      integer(c_int) :: arena                  
      !> This is the number of chunks not in use. (The memory allocator internally gets chunks of memory from the operating system, and then carves them up to satisfy individual malloc requests; see Efficiency and Malloc.)
      integer(c_int) :: ordblks        
      !> This field is unused.
      integer(c_int) :: smblks        
      !> This is the total number of chunks allocated with mmap.
      integer(c_int) :: hblks        
      !> This is the total size of memory allocated with mmap, in bytes.
      integer(c_int) :: hblkhd        
      !> This field is unused.
      integer(c_int) :: usmblks        
      !> This field is unused.
      integer(c_int) :: fsmblks        
      !> This is the total size of memory occupied by chunks handed out by malloc.
      integer(c_int) :: uordblks        
      !> This is the total size of memory occupied by free (not in use) chunks.
      integer(c_int) :: fordblks        
      !> This is the size of the top-most releasable chunk that normally borders the end of the heap (i.e., the high end of the virtual address space’s data segment).
      integer(c_int) :: keepcost      
    end type
    
    interface
      function mallinfo() bind(c, name="mallinfo") result(data)
        use :: iso_c_binding
        implicit none
        
        type, bind(c) :: MallInfo_t      
          integer(c_int) :: arena                        
          integer(c_int) :: ordblks              
          integer(c_int) :: smblks        
          integer(c_int) :: hblks        
          integer(c_int) :: hblkhd        
          integer(c_int) :: usmblks        
          integer(c_int) :: fsmblks        
          integer(c_int) :: uordblks        
          integer(c_int) :: fordblks        
          integer(c_int) :: keepcost      
        end type
        type(MallInfo_t) :: data
      end function
    end interface
  
  contains
  
  subroutine getMallocInfo(malinfo)
    implicit none
    type(MallInfo_t), intent(out) :: malinfo
    malinfo = mallinfo()
  end subroutine
  
  subroutine printMallInfo(malinfo)
    implicit none
    type(MallInfo_t), intent(in) :: malinfo
    write(*,*) "Total size of memory allocated with sbrk by malloc in byte.  ", malinfo%arena
    write(*,*) "Total size of memory allocated with mmap, in bytes.          ", malinfo%hblkhd
    write(*,*) "Total size of memory occupied by chunks handed out by malloc.", malinfo%uordblks
    write(*,*) "Total number of chunks allocated with mmap.                  ", malinfo%hblks
    write(*,*) "Number of chunks not in use.                                 ", malinfo%ordblks
    write(*,*) "Total size of memory occupied by free (not in use) chunks.   ", malinfo%fordblks
    write(*,*) "Size of the top-most releasable chunk borders end of the heap", malinfo%keepcost    
  end subroutine
  
  
end module

program test
  use MallocInfo_m
  implicit none
  type(MallInfo_t) :: mallinfos(10000)  
  integer :: i, nInfos
  integer, allocatable :: data(:)
  
  allocate(data(0))
  nInfos = 0
  do i=1, 10
    write(*,*) "Iteration",i
    deallocate(data)
    allocate(data(i*100000))
    nInfos = nInfos+1
    call getMallocInfo(mallinfos(nInfos))    
    call printMallInfo(mallInfos(nInfos))
    call sleep(1)
  end do
  
   do i=10, 1, -1
    write(*,*) "Iteration",i
    deallocate(data)
    allocate(data(i*100000))
    nInfos = nInfos+1
    call getMallocInfo(mallinfos(nInfos))    
    call printMallInfo(mallInfos(nInfos))    
    call sleep(1)
  end do
  
  write(*,*) "Total size of memory allocated with sbrk. min, mean, max", minval(mallinfos(1:nInfos)%arena), sum(mallinfos(1:nInfos)%arena)/nInfos, maxval(mallinfos(1:nInfos)%arena)
end program

./a.out
Iteration 1
Total size of memory allocated with sbrk by malloc in byte. 135168
Total size of memory allocated with mmap, in bytes. 401408
Total size of memory occupied by chunks handed out by malloc. 7080
Total number of chunks allocated with mmap. 1
Number of chunks not in use. 1
Total size of memory occupied by free (not in use) chunks. 128088
Size of the top-most releasable chunk borders end of the heap 128088
Iteration 2
Total size of memory allocated with sbrk by malloc in byte. 135168
Total size of memory allocated with mmap, in bytes. 802816
Total size of memory occupied by chunks handed out by malloc. 7080
Total number of chunks allocated with mmap. 1
Number of chunks not in use. 1
Total size of memory occupied by free (not in use) chunks. 128088
Size of the top-most releasable chunk borders end of the heap 128088
.
.
.
Total size of memory allocated with sbrk. min, mean, max 135168 155443 540672

18.02.2016

Nahkauf + Linux

Filed under: Allgemein — Tags: — Thomas @ 18:02

Der tolle Supermarkt nahkauf betreibt auf seinen Kassenrechnern Linux :D Ein Phoenix BIOS mit LILO Bootloader. Heute zufällig gesehen, als sie die Kiste neu gestartet hatten.
LILO.. das Zeug muss uralt sein. Oder hat jemand in den letzten 10 Jahren LILO installiert? :D :D :D

17.02.2016

Fortran: Detect 64bit 32bit

Filed under: Allgemein — Tags: — Thomas @ 08:02

Ein möglicher Weg zu erkennen ob auf einer 64bit oder 32bit Maschine compiliert wird ist mit Hilfe
von macros. Die üblichen macros wie __amd64, __amd64__, __x86_64 __x86_64__ funktionieren unter gfortran (nicht) mehr, da sie nur zeigen ob eine 64Bit Prozessor zur Verfügung steht. Und nicht, ob man
auch wirklich für 64bit compiliert. [1]
Es ist natürlich möglich untr 64bit OS für 32bit zu compilieren, wenn zum Beispiel nur ein 32bit Compiler zur Verfügung steht. Oder zu Testzwecken

Laut doku [2] steht zu diesem Zwecke das macro __LP64__ zur Verfügung.

__LP64__
_LP64
These macros are defined, with value 1, if (and only if) the compilation is for a target where long int and pointer both use 64-bits and int uses 32-bit.

Pointer ist 64bit und integer ist 32bit. So ist es richtig. Alle anderen (M$) machen es falsch.

Nun gibt es leider Compiler, die kein Preprocessing beherrschen. Zum Glück gibt es Fortran 2003
mit dem neuen iso_c_binding Modul. Das Symbol C_INTPTR_T repräsentiert die Größe eines
Pointers und kann als KIND parameter benutzt werden.


program main
  use, intrinsic :: iso_c_binding
  implicit none
  integer(kind=C_INTPTR_T) :: sizeofapointer
  
!__LP64__
!_LP64
! These macros are defined, with value 1, if (and only if) the compilation is for a target where long int and pointer both use 64-bits and int uses 32-bit. 
#ifdef __LP64__
  write(*,*) "64bit detected by macro"
#else
  write(*,*) "32bit detected by macro"
#endif

  write(*,*) "C_INTPTR_T",  C_INTPTR_T
end program

PS: Es ist möglich mit gfortran für 32bit zu compilieren. Einfach gfortran-multilib installieren
und dem Compiler -m32 geben.

[1] https://gcc.gnu.org/bugzilla/show_bug.cgi?id=47175
[2] https://gcc.gnu.org/onlinedocs/gcc-4.2.1/cpp/Common-Predefined-Macros.html

12.02.2016

/proc status

Filed under: Allgemein — Tags: — Thomas @ 20:02

Code snipped to read /proc status with fortran.
E.g. used memory and so...


! original: http://hiliev.eu/posts/recipe-obtaining-peak-vm-memory-size-in-pure-fortran.html

module ProcStatus
  contains
    !---------------------------------------------------------------!
    ! Returns current process virtual memory size             !
    ! Requires Linux procfs mounted at /proc                        !
    !---------------------------------------------------------------!
    ! Output: vmsize - vmsize VM size in kB                             !
    !---------------------------------------------------------------!
    function getVmSize() result(vmsize)
      implicit none
      integer :: vmsize
      character(len=80) :: stat_key, stat_value
      !
      vmsize = 0
      open(unit=1000, file="/proc/self/status", status='old', err=99)
      do while (.true.)
        read(unit=1000, fmt=*, err=88) stat_key, stat_value
        if (stat_key == 'VmSize:') then
          read(stat_value, *) vmsize
          exit
        end if
      end do
    88 close(unit=1000)
      if (vmsize == 0) goto 99
      return
      !
    99 print *, 'ERROR: procfs not mounted or not compatible'
      vmsize = -1
    end function getVmSize

end module ProcStatus

program test
  use ProcStatus
  implicit none
  integer :: vmsize
  integer, allocatable :: arr(:)

  allocate(arr(10000000)) ! ~ 40MB
  arr(:) = 0

  vmsize = getVmSize()
  print *, 'VM size: ', vmsize, ' kB'
end program test

02.02.2016

C gecaste (Bug of the day 10)

Filed under: Allgemein — Tags: — Thomas @ 10:02

Ist nicht direkt ein Bug, aber kann ganz leicht zu einem werden. Vorallem stört das rum-gecaste und Pointer auf locale Variablen. Hier ein Stück Code, wo ich erst drei mal hinschauen musste


typedef struct s_rocsmq_message {
...
} t_rocsmq_message, *p_rocsmq_message;

void func() {
  t_rocsmq_message message;
  rocsmq_recv(..., (p_rocsmq_message) & message, ROCSMQ_POLL)
}

Aber, ich sollte weniger mich beschweren, ehr Hilfe leisten.
Hier eine sehr einfache C++ version ohne Extras:


namespace rocs{
struct mqMessage {
...
};
}

using namespace rocs;
void func() {
  mqMessage message = mqRecv(...);
}

Keine Pointer, kein gecaste. Lokale Variable dann declariert und gleich initialisiert, wenn man sie braucht.
Projektname "rocs" aus den Datentypen und Funktionsnamen entfernt und in ein namespace ausgelagert. Verständlicher,
weniger Code, weniger Fehler.

29.01.2016

Programm Environment Modules

Filed under: Allgemein — Thomas @ 16:01

touch

dpkg -l | grep tcl
ii  libtcl8.5:amd64                        8.5.17-1                             amd64        Tcl (the Tool Command Language) v8.5 - run-time library files
ii  libtcl8.6:amd64                        8.6.2+dfsg-2                         amd64        Tcl (the Tool Command Language) v8.6 - run-time library files
ii  tcl                                    8.6.0+8                              amd64        Tool Command Language (default version) - shell
ii  tcl-dev:amd64                          8.6.0+8                              amd64        Tool Command Language (default version) - development files
ii  tcl8.5                                 8.5.17-1                             amd64        Tcl (the Tool Command Language) v8.5 - shell
ii  tcl8.5-dev:amd64                       8.5.17-1                             amd64        Tcl (the Tool Command Language) v8.5 - development files
ii  tcl8.6                                 8.6.2+dfsg-2                         amd64        Tcl (the Tool Command Language) v8.6 - shell
ii  tcl8.6-dev:amd64                       8.6.2+dfsg-2                         amd64        Tcl (the Tool Command Language) v8.6 - development files
ii  tclx8.4                                8.4.1-1                              amd64        Extended Tcl (TclX) - shared library
ii  tclx8.4-dev                            8.4.1-1                              amd64        Extended Tcl (TclX) - development package


 touch .spec.in
CPPFLAGS="-DUSE_INTERP_ERRORLINE" ./configure --with-tclx-lib=/usr/lib/ --with-tclx-inc=/usr/include/tclx8.4/ --with-tclx-ver=8.4

26.01.2016

Evaluation of logical operations

Filed under: Allgemein — Tags: , , — Thomas @ 21:01

Spass mit dem Standard.
Aus dem Fortran 90/95 Standard [1] Kapitel 7.1.7.6.

Evaluation of logical intrinsic operations
The rules given in 7.2.4 specify the interpretation of logical intrinsic operations. Once the
interpretation of an expression has been established in accordance with those rules, the processor
may evaluate any other expression that is logically equivalent, provided that the integrity of
parentheses in any expression is not violated.
NOTE 7.29
For example, for the variables L1, L2, and L3 of type logical, the processor may choose to
evaluate the expression
L1 .AND. L2 .AND. L3
as
L1 .AND. (L2 .AND. L3)
Two expressions of type logical are logically equivalent if their values are equal for all possible
values of their primaries.

Aus dem c++11 Standard [2] Kapitel 5.14

logical-and-expression
The && operator groups left-to-right.

Und die andern Operatoren auch left-to-right.

Aus dem C89 Standard [3] Kapitel 3.3

Except as indicated by the syntax27 or otherwise specified later (for the function-call operator () , && , || , ?: , and comma operators), the order of evaluation of subexpressions and the order in which side effects take place are both unspecified.

hf

[1] http://j3-fortran.org/doc/standing/archive/007/97-007r2/pdf/97-007r2.pdf
[2] http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf
[3] https://web.archive.org/web/20050207005628/http://dev.unicals.com/papers/c89-draft.html#3.3

« Newer PostsOlder Posts »

Powered by WordPress