while usando salir optimizacion lenguaje instruccion infinito for ejemplos codigo ciclo c performance intel instructions assembly

usando - Rendimiento de bucle de código C



salir de un ciclo while c++ (1)

Intenta usar perfiles EMON en Vtune, o alguna herramienta equivalente como oprof

EMON (Event Monitoring) profiling => como una herramienta basada en tiempo, pero puede decirle qué evento de rendimiento está causando el problema. Aunque, primero debe comenzar con un perfil basado en tiempo, para ver si hay una instrucción particular que salta. (Y posiblemente los eventos relacionados que le dicen con qué frecuencia hubo un puesto de retiro en esa IP).

Para usar perfiles de EMON, debe ejecutar una lista de eventos, que van desde "los sospechosos habituales" hasta ...

Aquí, comenzaría con errores de caché, alineación. No sé si el procesador que está utilizando tiene un contador para las limitaciones del puerto de RF (debería), pero agregué el perfil de EMON hace mucho tiempo, y no sé qué tan bien se mantienen al agregar eventos apropiados para la microarquitectura.

También es posible que sea un front-end, instrucción fetch, stall. ¿Cuántos bytes hay en estas instrucciones, de todos modos? También hay eventos EMON para eso.

Respondiendo para comentar que Nehalem VTune no puede ver eventos L3: no es cierto. Aquí hay cosas que estaba agregando para comentar, pero no encajaban:

En realidad, HAY contadores de rendimiento para LL3 / L3 $ / llamado Uncore. Me sorprendería inmensamente si VTune no los admite. Consulte http://software.intel.com/sites/products/collateral/hpc/vtune/performance_analysis_guide.pdf puntos para VTune y otras herramientas como PTU. De hecho, incluso sin eventos LL3, como dice David Levinthal: "el procesador Intel® Core ™ i7 tiene un" evento de latencia "que es muy similar al evento EAR de datos familiares del procesador Itanium®. Este evento muestra cargas, registrando el número de ciclos entre la ejecución de la instrucción y la entrega real de los datos. Si la latencia medida es mayor que la latencia mínima programada en MSR 0x3f6, bits 15: 0, entonces el contador se incrementa. El desbordamiento del contador arma el mecanismo PEBS y en el siguiente El evento que satisface el umbral de latencia, la latencia medida, la dirección virtual o lineal y el origen de datos se copian en 3 registros adicionales en el búfer PEBS. Como la dirección virtual se captura en una ubicación conocida, el controlador de muestreo también podría ejecutar un virtual para la traducción física y capturar la dirección física. La dirección física identifica la ubicación de inicio de la NUMA y, en principio, permite un análisis de los detalles de las ocupaciones de la memoria caché ". También señala, en la página 35, eventos de VTune como L3 CACHE_HIT_UNCORE_HIT y L3 CACHE_MISS_REMOTE_DRAM. A veces necesitas buscar los códigos numéricos y programarlos en la interfaz de nivel inferior de VTune, pero creo que en este caso es visible en la bonita interfaz de usuario.

OK, en http://software.intel.com/en-us/forums/showthread.php?t=77700&o=d&s=lr un programador de VTune en Rusia (creo) "explica" que no se puede muestrear en Uncore eventos.

Está equivocado: podría, por ejemplo, habilitar solo una CPU y tomar muestras de manera significativa. También creo que existe la posibilidad de marcar L3 datos faltantes a medida que regresa a la CPU. De hecho, en general, la L3 sabe a qué CPU está devolviendo datos, por lo que definitivamente puede probar. Es posible que no sepa qué hyperthread, pero de nuevo puede deshabilitar, pasar al modo de subproceso único.

Pero parece que, como es bastante común, tendrías que trabajar AROUND VTune, no con él, para hacer esto.

Pruebe primero con los perfiles de latencia. Eso está completamente dentro de la CPU, y es poco probable que la gente de VTune lo haya estropeado demasiado.

Y, lo repito, lo más probable es que su problema esté en el núcleo, no en L3. Entonces VTune debería ser capaz de manejar eso.

Pruebe "Contabilidad de ciclo" por Levinthal.

Esta pregunta continúa con mi pregunta aquí (siguiendo el consejo de Mystical):

Rendimiento de bucle de código C

Continuando con mi pregunta, cuando uso instrucciones empaquetadas en lugar de instrucciones escalares, el código que usa intrínsecos sería muy similar:

for(int i=0; i<size; i+=16) { y1 = _mm_load_ps(output[i]); … y4 = _mm_load_ps(output[i+12]); for(k=0; k<ksize; k++){ for(l=0; l<ksize; l++){ w = _mm_set_ps1(weight[i+k+l]); x1 = _mm_load_ps(input[i+k+l]); y1 = _mm_add_ps(y1,_mm_mul_ps(w,x1)); … x4 = _mm_load_ps(input[i+k+l+12]); y4 = _mm_add_ps(y4,_mm_mul_ps(w,x4)); } } _mm_store_ps(&output[i],y1); … _mm_store_ps(&output[i+12],y4); }

El rendimiento medido de este kernel es de aproximadamente 5.6 operaciones FP por ciclo, aunque esperaría que fuera exactamente 4 veces el rendimiento de la versión escalar, es decir, 4.1.6 = 6,4 operaciones FP por ciclo.

Teniendo en cuenta el movimiento del factor de peso (gracias por señalar eso), el calendario se ve así:

Parece que el programa no cambia, aunque hay una instrucción adicional después de la operación movss que mueve el valor de peso escalar al registro XMM y luego usa shufps para copiar este valor escalar en todo el vector. Parece que el vector de ponderación está listo para ser utilizado por los mulps en el tiempo teniendo en cuenta la latencia de conmutación de la carga al dominio de coma flotante, por lo que esto no debería generar ninguna latencia adicional.

Las movaps (alineadas, movaps empaquetadas), addps y mulps que se usan en este kernel (verificadas con código ensamblador) tienen la misma latencia y rendimiento que sus versiones escalares, por lo que esto tampoco debería generar latencia adicional.

¿Alguien tiene una idea de dónde se gasta este ciclo extra por cada 8 ciclos, suponiendo que el rendimiento máximo que este kernel puede obtener es de 6.4 FP ops por ciclo y se está ejecutando en 5.6 FP ops por ciclo?

Por cierto, aquí es cómo se ve el ensamblaje real:

… Block x: movapsx (%rax,%rcx,4), %xmm0 movapsx 0x10(%rax,%rcx,4), %xmm1 movapsx 0x20(%rax,%rcx,4), %xmm2 movapsx 0x30(%rax,%rcx,4), %xmm3 movssl (%rdx,%rcx,4), %xmm4 inc %rcx shufps $0x0, %xmm4, %xmm4 {fill weight vector} cmp $0x32, %rcx mulps %xmm4, %xmm0 mulps %xmm4, %xmm1 mulps %xmm4, %xmm2 mulps %xmm3, %xmm4 addps %xmm0, %xmm5 addps %xmm1, %xmm6 addps %xmm2, %xmm7 addps %xmm4, %xmm8 jl 0x401ad6 <Block x> …