Changes in / [31bb2e1:4ec028d]


Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • libcfa/src/concurrency/io.cfa

    r31bb2e1 r4ec028d  
    576576                                int count;
    577577                                bool again;
    578                                 [count, again] = __drain_io( ring, &mask, 1, true );
     578                                [count, again] = __drain_io( ring, &mask, 0, true );
    579579
    580580                                // Update statistics
     
    589589
    590590                unregister( &ring.poller.slow.id );
     591
     592                #if !defined(__CFA_NO_STATISTICS__)
     593                        __tally_stats(cltr->stats, &local_stats);
     594                #endif
    591595
    592596                return 0p;
     
    726730        }
    727731
     732        static inline uint32_t __submit_to_ready_array( struct __io_data & ring, uint32_t idx, const uint32_t mask ) {
     733                /* paranoid */ verify( idx <= mask   );
     734                /* paranoid */ verify( idx != -1ul32 );
     735
     736                // We need to find a spot in the ready array
     737                __attribute((unused)) int len   = 0;
     738                __attribute((unused)) int block = 0;
     739                uint32_t ready_mask = ring.submit_q.ready_cnt - 1;
     740
     741                disable_interrupts();
     742                        uint32_t off = __tls_rand();
     743                enable_interrupts( __cfaabi_dbg_ctx );
     744
     745                uint32_t picked;
     746                LOOKING: for() {
     747                        for(i; ring.submit_q.ready_cnt) {
     748                                picked = (i + off) & ready_mask;
     749                                uint32_t expected = -1ul32;
     750                                if( __atomic_compare_exchange_n( &ring.submit_q.ready[picked], &expected, idx, true, __ATOMIC_SEQ_CST, __ATOMIC_RELAXED ) ) {
     751                                        break LOOKING;
     752                                }
     753                                verify(expected != idx);
     754
     755                                len ++;
     756                        }
     757
     758                        block++;
     759                        yield();
     760                }
     761
     762                // update statistics
     763                #if !defined(__CFA_NO_STATISTICS__)
     764                disable_interrupts();
     765                        __tls_stats()->io.submit_q.look_avg.val   += len;
     766                        __tls_stats()->io.submit_q.look_avg.block += block;
     767                        __tls_stats()->io.submit_q.look_avg.cnt   += 1;
     768                enable_interrupts( __cfaabi_dbg_ctx );
     769                #endif
     770
     771                return picked;
     772        }
     773
    728774        void __submit( struct __io_data & ring, uint32_t idx ) {
    729775                // Get now the data we definetely need
     
    731777                const uint32_t mask = *ring.submit_q.mask;
    732778
    733                 disable_interrupts();
    734 
    735779                // There are 2 submission schemes, check which one we are using
    736780                if( ring.cltr_flags & CFA_CLUSTER_IO_POLLER_THREAD_SUBMITS ) {
    737781                        // If the poller thread submits, then we just need to add this to the ready array
    738782
    739                         /* paranoid */ verify( idx <= mask   );
    740                         /* paranoid */ verify( idx != -1ul32 );
    741 
    742                         // We need to find a spot in the ready array
    743                         __attribute((unused)) int len   = 0;
    744                         __attribute((unused)) int block = 0;
    745                         uint32_t ready_mask = ring.submit_q.ready_cnt - 1;
    746                         uint32_t off = __tls_rand();
    747                         LOOKING: for() {
    748                                 for(i; ring.submit_q.ready_cnt) {
    749                                         uint32_t ii = (i + off) & ready_mask;
    750                                         uint32_t expected = -1ul32;
    751                                         if( __atomic_compare_exchange_n( &ring.submit_q.ready[ii], &expected, idx, true, __ATOMIC_SEQ_CST, __ATOMIC_RELAXED ) ) {
    752                                                 break LOOKING;
    753                                         }
    754                                         verify(expected != idx);
    755 
    756                                         len ++;
    757                                 }
    758 
    759                                 block++;
    760                                 yield();
    761                         }
     783                        __submit_to_ready_array( ring, idx, mask );
    762784
    763785                        __wake_poller( ring );
    764 
    765                         // update statistics
    766                         #if !defined(__CFA_NO_STATISTICS__)
    767                                 __tls_stats()->io.submit_q.look_avg.val   += len;
    768                                 __tls_stats()->io.submit_q.look_avg.block += block;
    769                                 __tls_stats()->io.submit_q.look_avg.cnt   += 1;
    770                         #endif
    771786
    772787                        __cfadbg_print_safe( io, "Kernel I/O : Added %u to ready for %p\n", idx, active_thread() );
     
    804819                        __cfadbg_print_safe( io, "Kernel I/O : Performed io_submit for %p, returned %d\n", active_thread(), ret );
    805820                }
    806 
    807                 enable_interrupts( __cfaabi_dbg_ctx );
    808         }
    809 
    810         static inline void ?{}(struct io_uring_sqe & this, uint8_t opcode, int fd) {
    811                 this.opcode = opcode;
    812                 #if !defined(IOSQE_ASYNC)
    813                         this.flags = 0;
    814                 #else
    815                         this.flags = IOSQE_ASYNC;
    816                 #endif
    817                 this.ioprio = 0;
    818                 this.fd = fd;
    819                 this.off = 0;
    820                 this.addr = 0;
    821                 this.len = 0;
    822                 this.rw_flags = 0;
    823                 this.__pad2[0] = this.__pad2[1] = this.__pad2[2] = 0;
    824         }
    825 
    826         static inline void ?{}(struct io_uring_sqe & this, uint8_t opcode, int fd, void * addr, uint32_t len, uint64_t off ) {
    827                 (this){ opcode, fd };
    828                 this.off = off;
    829                 this.addr = (uint64_t)(uintptr_t)addr;
    830                 this.len = len;
    831         }
     821        }
     822#endif
Note: See TracChangeset for help on using the changeset viewer.