bfc1508d (kx 2023-03-24 03:55:33 +0300 1)
bfc1508d (kx 2023-03-24 03:55:33 +0300 2) #ifdef HAVE_CONFIG_H
bfc1508d (kx 2023-03-24 03:55:33 +0300 3) #include <config.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 4) #endif
bfc1508d (kx 2023-03-24 03:55:33 +0300 5)
bfc1508d (kx 2023-03-24 03:55:33 +0300 6) #include <stdlib.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 7) #include <stdio.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 8) #include <sys/sysinfo.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 9) #include <sys/types.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 10) #ifdef HAVE_INTTYPES_H
bfc1508d (kx 2023-03-24 03:55:33 +0300 11) #include <inttypes.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 12) #else
bfc1508d (kx 2023-03-24 03:55:33 +0300 13) #include <stdint.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 14) #endif
bfc1508d (kx 2023-03-24 03:55:33 +0300 15) #include <stddef.h> /* offsetof(3) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 16) #include <dirent.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 17) #include <sys/stat.h> /* chmod(2) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 18) #include <sys/file.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 19) #include <sys/mman.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 20) #include <fcntl.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 21) #include <limits.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 22) #include <string.h> /* strdup(3) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 23) #include <libgen.h> /* basename(3) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 24) #include <ctype.h> /* tolower(3) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 25) #include <errno.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 26) #include <time.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 27) #include <sys/time.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 28) #include <pwd.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 29) #include <grp.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 30) #include <stdarg.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 31) #include <locale.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 32) #include <unistd.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 33)
bfc1508d (kx 2023-03-24 03:55:33 +0300 34) #include <libxml/parser.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 35) #include <libxml/tree.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 36)
bfc1508d (kx 2023-03-24 03:55:33 +0300 37) #include <nls.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 38)
bfc1508d (kx 2023-03-24 03:55:33 +0300 39) #include <defs.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 40)
bfc1508d (kx 2023-03-24 03:55:33 +0300 41) #include <fatal.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 42) #include <http.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 43) #include <html.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 44)
bfc1508d (kx 2023-03-24 03:55:33 +0300 45) #include <cmpvers.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 46) #include <dlist.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 47) #include <strbuf.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 48) #include <repolist.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 49) #include <wrapper.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 50) #include <system.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 51) #include <date.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 52)
bfc1508d (kx 2023-03-24 03:55:33 +0300 53) #include <ctx.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 54) #include <ui-shared.h>
bfc1508d (kx 2023-03-24 03:55:33 +0300 55)
bfc1508d (kx 2023-03-24 03:55:33 +0300 56)
bfc1508d (kx 2023-03-24 03:55:33 +0300 57) /********************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 58) Sorted dlist functions:
bfc1508d (kx 2023-03-24 03:55:33 +0300 59) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 60) struct tree_line {
bfc1508d (kx 2023-03-24 03:55:33 +0300 61) char *name;
bfc1508d (kx 2023-03-24 03:55:33 +0300 62) char *revision;
bfc1508d (kx 2023-03-24 03:55:33 +0300 63) char *date;
bfc1508d (kx 2023-03-24 03:55:33 +0300 64) char *size;
bfc1508d (kx 2023-03-24 03:55:33 +0300 65) };
bfc1508d (kx 2023-03-24 03:55:33 +0300 66)
bfc1508d (kx 2023-03-24 03:55:33 +0300 67) static struct dlist *directories = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 68) static struct dlist *files = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 69)
bfc1508d (kx 2023-03-24 03:55:33 +0300 70) static struct tree_line *tree_line_alloc( const char *name, const char *revision, const char *date, const char *size )
bfc1508d (kx 2023-03-24 03:55:33 +0300 71) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 72) struct tree_line *line = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 73) line = (struct tree_line *)xmalloc( sizeof(struct tree_line) );
bfc1508d (kx 2023-03-24 03:55:33 +0300 74)
bfc1508d (kx 2023-03-24 03:55:33 +0300 75) if( name ) { line->name = xstrdup( name ); }
bfc1508d (kx 2023-03-24 03:55:33 +0300 76) if( revision ) { line->revision = xstrdup( revision ); }
bfc1508d (kx 2023-03-24 03:55:33 +0300 77) if( date ) { line->date = xstrdup( date ); }
bfc1508d (kx 2023-03-24 03:55:33 +0300 78) if( size ) { line->size = xstrdup( size ); }
bfc1508d (kx 2023-03-24 03:55:33 +0300 79)
bfc1508d (kx 2023-03-24 03:55:33 +0300 80) return line;
bfc1508d (kx 2023-03-24 03:55:33 +0300 81) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 82)
bfc1508d (kx 2023-03-24 03:55:33 +0300 83) static void __line_free( void *data, void *user_data )
bfc1508d (kx 2023-03-24 03:55:33 +0300 84) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 85) struct tree_line *line = (struct tree_line *)data;
bfc1508d (kx 2023-03-24 03:55:33 +0300 86) if( line )
bfc1508d (kx 2023-03-24 03:55:33 +0300 87) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 88) if( line->name ) { free( line->name ); line->name = NULL; }
bfc1508d (kx 2023-03-24 03:55:33 +0300 89) if( line->revision ) { free( line->revision ); line->revision = NULL; }
bfc1508d (kx 2023-03-24 03:55:33 +0300 90) if( line->date ) { free( line->date ); line->date = NULL; }
bfc1508d (kx 2023-03-24 03:55:33 +0300 91) if( line->size ) { free( line->size ); line->size = NULL; }
bfc1508d (kx 2023-03-24 03:55:33 +0300 92)
bfc1508d (kx 2023-03-24 03:55:33 +0300 93) free( line );
bfc1508d (kx 2023-03-24 03:55:33 +0300 94) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 95) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 96)
bfc1508d (kx 2023-03-24 03:55:33 +0300 97) static struct dlist *tree_lines_free( struct dlist *lines )
bfc1508d (kx 2023-03-24 03:55:33 +0300 98) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 99) if( lines )
bfc1508d (kx 2023-03-24 03:55:33 +0300 100) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 101) dlist_free( lines, __line_free );
bfc1508d (kx 2023-03-24 03:55:33 +0300 102) lines = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 103) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 104) return lines;
bfc1508d (kx 2023-03-24 03:55:33 +0300 105) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 106)
bfc1508d (kx 2023-03-24 03:55:33 +0300 107) static int __cmp_tree_lines_bytag( const void *a, const void *b )
bfc1508d (kx 2023-03-24 03:55:33 +0300 108) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 109) char *v1 = NULL, *v2 = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 110) int ret = -1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 111)
bfc1508d (kx 2023-03-24 03:55:33 +0300 112) struct tree_line *line1 = (struct tree_line *)a;
bfc1508d (kx 2023-03-24 03:55:33 +0300 113) struct tree_line *line2 = (struct tree_line *)b;
bfc1508d (kx 2023-03-24 03:55:33 +0300 114)
bfc1508d (kx 2023-03-24 03:55:33 +0300 115) if( line1->name && line2->name )
bfc1508d (kx 2023-03-24 03:55:33 +0300 116) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 117) v1 = line1->name;
bfc1508d (kx 2023-03-24 03:55:33 +0300 118) v2 = line2->name;
bfc1508d (kx 2023-03-24 03:55:33 +0300 119) while( *v1 && !isdigit( *v1 ) ) ++v1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 120) while( *v2 && !isdigit( *v2 ) ) ++v2;
bfc1508d (kx 2023-03-24 03:55:33 +0300 121) ret = strcmp( line1->name, line2->name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 122) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 123) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 124) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 125)
bfc1508d (kx 2023-03-24 03:55:33 +0300 126) if( !*v1 || !*v2 )
bfc1508d (kx 2023-03-24 03:55:33 +0300 127) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 128) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 129) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 130)
bfc1508d (kx 2023-03-24 03:55:33 +0300 131) /******************************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 132) sort reversive to show newest tag first:
bfc1508d (kx 2023-03-24 03:55:33 +0300 133) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 134) return -cmp_version( (const char *)v1, (const char *)v2 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 135) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 136)
bfc1508d (kx 2023-03-24 03:55:33 +0300 137) static struct dlist *tree_lines_sort_bytag( struct dlist *lines )
bfc1508d (kx 2023-03-24 03:55:33 +0300 138) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 139) if( lines ) { lines = dlist_sort( lines, __cmp_tree_lines_bytag ); }
bfc1508d (kx 2023-03-24 03:55:33 +0300 140) return lines;
bfc1508d (kx 2023-03-24 03:55:33 +0300 141) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 142) /*
bfc1508d (kx 2023-03-24 03:55:33 +0300 143) End of sorted dlist functions.
bfc1508d (kx 2023-03-24 03:55:33 +0300 144) ********************************/
bfc1508d (kx 2023-03-24 03:55:33 +0300 145)
bfc1508d (kx 2023-03-24 03:55:33 +0300 146)
bfc1508d (kx 2023-03-24 03:55:33 +0300 147) static const char *is_file_executable( const char *relative_path, const char *name, int revision )
bfc1508d (kx 2023-03-24 03:55:33 +0300 148) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 149) const char *co_prefix = ctx.repo.checkout_ro_prefix;
c7693c71 (kx 2023-04-12 19:21:06 +0300 150) const char *repo_name = ctx.repo.name;
c7693c71 (kx 2023-04-12 19:21:06 +0300 151) const char *repo_root = ctx.repo.repo_root;
bfc1508d (kx 2023-03-24 03:55:33 +0300 152) const char *ret = "";
bfc1508d (kx 2023-03-24 03:55:33 +0300 153) char *path = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 154)
bfc1508d (kx 2023-03-24 03:55:33 +0300 155) if( !name ) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 156)
bfc1508d (kx 2023-03-24 03:55:33 +0300 157) if( relative_path && *relative_path )
bfc1508d (kx 2023-03-24 03:55:33 +0300 158) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 159) path = (char *)xmalloc( strlen( relative_path ) + 2 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 160) path[0] = '/';
bfc1508d (kx 2023-03-24 03:55:33 +0300 161) sprintf( (char *)&path[1], relative_path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 162) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 163) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 164) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 165) path = (char *)xmalloc( 1 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 166) path[0] = '\0';
bfc1508d (kx 2023-03-24 03:55:33 +0300 167) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 168)
bfc1508d (kx 2023-03-24 03:55:33 +0300 169) if( co_prefix )
bfc1508d (kx 2023-03-24 03:55:33 +0300 170) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 171) char repo_path[PATH_MAX] = { 0 };
c7693c71 (kx 2023-04-12 19:21:06 +0300 172) char cmd[PATH_MAX];
bfc1508d (kx 2023-03-24 03:55:33 +0300 173) struct strbuf buf = STRBUF_INIT;
bfc1508d (kx 2023-03-24 03:55:33 +0300 174) pid_t p = (pid_t) -1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 175) int rc;
bfc1508d (kx 2023-03-24 03:55:33 +0300 176)
c7693c71 (kx 2023-04-12 19:21:06 +0300 177) if( repo_root && *repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 178) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 179) strcat( (char *)&repo_path[0], repo_root );
c7693c71 (kx 2023-04-12 19:21:06 +0300 180) strcat( (char *)&repo_path[0], "/" );
c7693c71 (kx 2023-04-12 19:21:06 +0300 181) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 182) strcat( (char *)&repo_path[0], repo_name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 183)
bfc1508d (kx 2023-03-24 03:55:33 +0300 184) if( revision )
bfc1508d (kx 2023-03-24 03:55:33 +0300 185) snprintf( (char *)&cmd[0], 1024,
bfc1508d (kx 2023-03-24 03:55:33 +0300 186) "svn propget svn:executable --revision %d %s/%s%s/%s 2>/dev/null",
c7693c71 (kx 2023-04-12 19:21:06 +0300 187) revision, co_prefix, (char *)&repo_path[0], path, name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 188) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 189) snprintf( (char *)&cmd[0], 1024,
bfc1508d (kx 2023-03-24 03:55:33 +0300 190) "svn propget svn:executable %s/%s%s/%s 2>/dev/null",
c7693c71 (kx 2023-04-12 19:21:06 +0300 191) co_prefix, (char *)&repo_path[0], path, name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 192) p = sys_exec_command( &buf, cmd );
bfc1508d (kx 2023-03-24 03:55:33 +0300 193) rc = sys_wait_command( p, NULL );
bfc1508d (kx 2023-03-24 03:55:33 +0300 194) if( rc != 0 )
bfc1508d (kx 2023-03-24 03:55:33 +0300 195) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 196) strbuf_release( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 197) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 198) return "";
bfc1508d (kx 2023-03-24 03:55:33 +0300 199) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 200)
bfc1508d (kx 2023-03-24 03:55:33 +0300 201) strbuf_trim( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 202) if( buf.buf[0] == '*' )
bfc1508d (kx 2023-03-24 03:55:33 +0300 203) ret = " exec";
bfc1508d (kx 2023-03-24 03:55:33 +0300 204) strbuf_release( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 205) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 206)
bfc1508d (kx 2023-03-24 03:55:33 +0300 207) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 208) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 209) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 210)
bfc1508d (kx 2023-03-24 03:55:33 +0300 211)
bfc1508d (kx 2023-03-24 03:55:33 +0300 212) static xmlNode *xml_find_node_by_name( xmlNode *root, const char *name )
bfc1508d (kx 2023-03-24 03:55:33 +0300 213) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 214) xmlNode *node = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 215) xmlNode *ret = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 216)
bfc1508d (kx 2023-03-24 03:55:33 +0300 217) if( !name || !*name || !root || !root->children ) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 218)
bfc1508d (kx 2023-03-24 03:55:33 +0300 219) for( node = root->children; node; node = node->next )
bfc1508d (kx 2023-03-24 03:55:33 +0300 220) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 221) if( node->type == XML_ELEMENT_NODE )
bfc1508d (kx 2023-03-24 03:55:33 +0300 222) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 223) if( !strcmp( (char *)name, (char *)node->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 224) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 225) return node;
bfc1508d (kx 2023-03-24 03:55:33 +0300 226) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 227) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 228) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 229) return ret;
bfc1508d (kx 2023-03-24 03:55:33 +0300 230) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 231)
bfc1508d (kx 2023-03-24 03:55:33 +0300 232) static void xml_csvn_tree( const struct strbuf *buf )
bfc1508d (kx 2023-03-24 03:55:33 +0300 233) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 234) xmlDocPtr doc = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 235) xmlNode *root = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 236)
bfc1508d (kx 2023-03-24 03:55:33 +0300 237) if( !buf || !buf->buf ) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 238)
bfc1508d (kx 2023-03-24 03:55:33 +0300 239) LIBXML_TEST_VERSION
bfc1508d (kx 2023-03-24 03:55:33 +0300 240)
bfc1508d (kx 2023-03-24 03:55:33 +0300 241) doc = xmlReadMemory( buf->buf, buf->len, "list.xml", NULL, 0 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 242) if( !doc )
bfc1508d (kx 2023-03-24 03:55:33 +0300 243) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 244) html_fatal( "cannot parse svn list.xml" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 245) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 246) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 247)
bfc1508d (kx 2023-03-24 03:55:33 +0300 248) root = xmlDocGetRootElement( doc );
bfc1508d (kx 2023-03-24 03:55:33 +0300 249) if( !root )
bfc1508d (kx 2023-03-24 03:55:33 +0300 250) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 251) xmlFreeDoc( doc );
bfc1508d (kx 2023-03-24 03:55:33 +0300 252) xmlCleanupParser();
bfc1508d (kx 2023-03-24 03:55:33 +0300 253) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 254) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 255)
bfc1508d (kx 2023-03-24 03:55:33 +0300 256) if( !strcmp( "lists", (char *)root->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 257) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 258) xmlNode *list = NULL, *node = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 259)
bfc1508d (kx 2023-03-24 03:55:33 +0300 260) list = xml_find_node_by_name( root, "list" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 261) if( !list )
bfc1508d (kx 2023-03-24 03:55:33 +0300 262) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 263) xmlFreeDoc( doc );
bfc1508d (kx 2023-03-24 03:55:33 +0300 264) xmlCleanupParser();
bfc1508d (kx 2023-03-24 03:55:33 +0300 265) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 266) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 267)
bfc1508d (kx 2023-03-24 03:55:33 +0300 268) /****************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 269) Collect directories first:
bfc1508d (kx 2023-03-24 03:55:33 +0300 270) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 271) for( node = list->children; node; node = node->next )
bfc1508d (kx 2023-03-24 03:55:33 +0300 272) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 273) if( node->type == XML_ELEMENT_NODE && !strcmp( "entry", (char *)node->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 274) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 275) xmlChar *content = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 276) xmlNode *param = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 277)
bfc1508d (kx 2023-03-24 03:55:33 +0300 278) content = xmlGetProp( node, (const unsigned char *)"kind" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 279) if( !strcmp( (const char *)content, "dir" ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 280) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 281) xmlChar *name = NULL, *revision = NULL, *date = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 282)
bfc1508d (kx 2023-03-24 03:55:33 +0300 283) for( param = node->children; param; param= param->next )
bfc1508d (kx 2023-03-24 03:55:33 +0300 284) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 285) if( param->type == XML_ELEMENT_NODE && !strcmp( "name", (char *)param->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 286) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 287) name = xmlNodeGetContent( param );
bfc1508d (kx 2023-03-24 03:55:33 +0300 288) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 289) if( param->type == XML_ELEMENT_NODE && !strcmp( "commit", (char *)param->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 290) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 291) xmlNode *commit_date = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 292) revision = xmlGetProp( param, (const unsigned char *)"revision" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 293) commit_date = xml_find_node_by_name( param, "date" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 294) if( commit_date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 295) date = xmlNodeGetContent( commit_date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 296) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 297) } /* End for entry parameters */
bfc1508d (kx 2023-03-24 03:55:33 +0300 298)
bfc1508d (kx 2023-03-24 03:55:33 +0300 299) if( name && revision && date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 300) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 301) struct tree_line *line = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 302)
bfc1508d (kx 2023-03-24 03:55:33 +0300 303) line = tree_line_alloc( (const char *)name, (const char *)revision, (const char *)date, NULL );
bfc1508d (kx 2023-03-24 03:55:33 +0300 304) directories = dlist_append( directories, (void *)line );
bfc1508d (kx 2023-03-24 03:55:33 +0300 305)
bfc1508d (kx 2023-03-24 03:55:33 +0300 306) xmlFree( name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 307) xmlFree( revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 308) xmlFree( date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 309) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 310) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 311) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 312) if( name ) xmlFree( name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 313) if( revision ) xmlFree( revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 314) if( date ) xmlFree( date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 315) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 316) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 317) xmlFree( content );
bfc1508d (kx 2023-03-24 03:55:33 +0300 318) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 319) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 320)
bfc1508d (kx 2023-03-24 03:55:33 +0300 321) /****************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 322) Collect files:
bfc1508d (kx 2023-03-24 03:55:33 +0300 323) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 324) for( node = list->children; node; node = node->next )
bfc1508d (kx 2023-03-24 03:55:33 +0300 325) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 326) if( node->type == XML_ELEMENT_NODE && !strcmp( "entry", (char *)node->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 327) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 328) xmlChar *content = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 329) xmlNode *param = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 330)
bfc1508d (kx 2023-03-24 03:55:33 +0300 331) content = xmlGetProp( node, (const unsigned char *)"kind" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 332) if( !strcmp( (const char *)content, "file" ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 333) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 334) xmlChar *name = NULL, *size = NULL, *revision = NULL, *date = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 335)
bfc1508d (kx 2023-03-24 03:55:33 +0300 336) for( param = node->children; param; param= param->next )
bfc1508d (kx 2023-03-24 03:55:33 +0300 337) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 338) if( param->type == XML_ELEMENT_NODE && !strcmp( "name", (char *)param->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 339) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 340) name = xmlNodeGetContent( param );
bfc1508d (kx 2023-03-24 03:55:33 +0300 341) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 342) if( param->type == XML_ELEMENT_NODE && !strcmp( "size", (char *)param->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 343) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 344) size = xmlNodeGetContent( param );
bfc1508d (kx 2023-03-24 03:55:33 +0300 345) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 346) if( param->type == XML_ELEMENT_NODE && !strcmp( "commit", (char *)param->name ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 347) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 348) xmlNode *commit_date = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 349) revision = xmlGetProp( param, (const unsigned char *)"revision" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 350) commit_date = xml_find_node_by_name( param, "date" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 351) if( commit_date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 352) date = xmlNodeGetContent( commit_date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 353) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 354) } /* End for entry parameters */
bfc1508d (kx 2023-03-24 03:55:33 +0300 355)
bfc1508d (kx 2023-03-24 03:55:33 +0300 356) if( name && size && revision && date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 357) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 358) struct tree_line *line = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 359)
bfc1508d (kx 2023-03-24 03:55:33 +0300 360) line = tree_line_alloc( (const char *)name, (const char *)revision, (const char *)date, (const char *)size );
bfc1508d (kx 2023-03-24 03:55:33 +0300 361) files = dlist_append( files, (void *)line );
bfc1508d (kx 2023-03-24 03:55:33 +0300 362)
bfc1508d (kx 2023-03-24 03:55:33 +0300 363) xmlFree( name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 364) xmlFree( size );
bfc1508d (kx 2023-03-24 03:55:33 +0300 365) xmlFree( revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 366) xmlFree( date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 367) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 368) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 369) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 370) if( name ) xmlFree( name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 371) if( size ) xmlFree( size );
bfc1508d (kx 2023-03-24 03:55:33 +0300 372) if( revision ) xmlFree( revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 373) if( date ) xmlFree( date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 374) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 375) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 376) xmlFree( content );
bfc1508d (kx 2023-03-24 03:55:33 +0300 377) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 378) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 379) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 380)
bfc1508d (kx 2023-03-24 03:55:33 +0300 381) xmlFreeDoc(doc);
bfc1508d (kx 2023-03-24 03:55:33 +0300 382) xmlCleanupParser();
bfc1508d (kx 2023-03-24 03:55:33 +0300 383) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 384)
bfc1508d (kx 2023-03-24 03:55:33 +0300 385)
bfc1508d (kx 2023-03-24 03:55:33 +0300 386) static void dlist_csvn_tree( struct strbuf *sb, const char *relative_path, int rev )
bfc1508d (kx 2023-03-24 03:55:33 +0300 387) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 388) char *path = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 389)
bfc1508d (kx 2023-03-24 03:55:33 +0300 390) if( !sb || !sb->len ) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 391)
bfc1508d (kx 2023-03-24 03:55:33 +0300 392) if( relative_path && *relative_path )
bfc1508d (kx 2023-03-24 03:55:33 +0300 393) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 394) path = (char *)xmalloc( strlen( relative_path ) + 2 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 395) path[0] = '/';
bfc1508d (kx 2023-03-24 03:55:33 +0300 396) sprintf( (char *)&path[1], relative_path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 397) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 398) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 399) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 400) path = (char *)xmalloc( 1 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 401) path[0] = '\0';
bfc1508d (kx 2023-03-24 03:55:33 +0300 402) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 403)
bfc1508d (kx 2023-03-24 03:55:33 +0300 404) if( path && *path && !strcmp( (char *)&path[1], ctx.repo.tags ) )
bfc1508d (kx 2023-03-24 03:55:33 +0300 405) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 406) directories = tree_lines_sort_bytag( directories );
bfc1508d (kx 2023-03-24 03:55:33 +0300 407) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 408)
bfc1508d (kx 2023-03-24 03:55:33 +0300 409) strbuf_addstr( sb, "\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 410) strbuf_addf( sb, " <div class=\"repo-tree-header\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 411) strbuf_addf( sb, " <div class=\"row\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 412) strbuf_addf( sb, " <div class=\"col-path\">Path</div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 413) strbuf_addf( sb, " <div class=\"col-size\"><div class=\"tree-size trunc\">Size</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 414) strbuf_addf( sb, " <div class=\"col-rev\"><div class=\"tree-rev trunc\">Rev</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 415) strbuf_addf( sb, " <div class=\"col-date\"><div class=\"tree-date trunc\">Date</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 416) strbuf_addf( sb, " <div class=\"col-links\"><div class=\"tree-links trunc\">Links</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 417) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 418) strbuf_addf( sb, " </div>\n\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 419)
bfc1508d (kx 2023-03-24 03:55:33 +0300 420) strbuf_addf( sb, " <div class=\"tree\">\n\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 421)
bfc1508d (kx 2023-03-24 03:55:33 +0300 422) /**************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 423) Print directories first:
bfc1508d (kx 2023-03-24 03:55:33 +0300 424) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 425) if( directories )
bfc1508d (kx 2023-03-24 03:55:33 +0300 426) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 427) struct dlist *list = directories;
bfc1508d (kx 2023-03-24 03:55:33 +0300 428) while( list )
bfc1508d (kx 2023-03-24 03:55:33 +0300 429) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 430) struct tree_line *line = (struct tree_line *)list->data;
bfc1508d (kx 2023-03-24 03:55:33 +0300 431)
bfc1508d (kx 2023-03-24 03:55:33 +0300 432) if( line->name && line->revision && line->date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 433) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 434) struct tm tm;
bfc1508d (kx 2023-03-24 03:55:33 +0300 435) time_t time = -1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 436) const char *query_string = ctx_remove_query_param( ctx.env.query_string, "rev" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 437)
bfc1508d (kx 2023-03-24 03:55:33 +0300 438) query_string = ctx_remove_query_param( query_string, "op" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 439)
bfc1508d (kx 2023-03-24 03:55:33 +0300 440) time = parse_date( &tm, (const char *)line->date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 441)
bfc1508d (kx 2023-03-24 03:55:33 +0300 442) strbuf_addf( sb, " <div class=\"row\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 443) if( ctx.env.query_string && *ctx.env.query_string )
c7693c71 (kx 2023-04-12 19:21:06 +0300 444) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 445) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 446) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 447) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s/%s%s/%s/?%s\"><div class=\"tree-path dir\">%s/</div></a></div>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, ctx.env.query_string, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 448) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 449) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 450) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 451) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s%s/%s/?%s\"><div class=\"tree-path dir\">%s/</div></a></div>\n", ctx.repo.name, path, line->name, ctx.env.query_string, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 452) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 453) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 454) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 455) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 456) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 457) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 458) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s/%s%s/%s/\"><div class=\"tree-path dir\">%s/</div></a></div>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 459) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 460) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 461) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 462) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s%s/%s/\"><div class=\"tree-path dir\">%s/</div></a></div>\n", ctx.repo.name, path, line->name, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 463) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 464) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 465) strbuf_addf( sb, " <div class=\"col-size\"><div onclick=\"trunc(this)\" class=\"tree-size trunc\">4096</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 466) strbuf_addf( sb, " <div class=\"col-rev\"><div onclick=\"trunc(this)\" class=\"tree-rev trunc\">%s</div></div>\n", line->revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 467) if( time != -1 )
bfc1508d (kx 2023-03-24 03:55:33 +0300 468) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 469) strbuf_addf( sb, " <div class=\"col-date\"><div onclick=\"trunc(this)\" class=\"tree-date trunc\">" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 470) csvn_print_age( sb, time, 0, 0 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 471) strbuf_addf( sb, "</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 472) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 473) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 474) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 475) strbuf_addf( sb, " <div class=\"col-date\"><div onclick=\"trunc(this)\" class=\"tree-date trunc\">unknown</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 476) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 477) strbuf_addf( sb, " <div class=\"col-links\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 478) strbuf_addf( sb, " <div onclick=\"trunc(this)\" class=\"tree-links trunc\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 479) if( query_string && *query_string )
bfc1508d (kx 2023-03-24 03:55:33 +0300 480) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 481) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 482) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 483) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=log&rev=%s&%s\">log</a> \n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 484) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=diff&rev=%s&%s\">diff</a>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 485) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 486) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 487) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 488) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=log&rev=%s&%s\">log</a> \n", ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 489) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=diff&rev=%s&%s\">diff</a>\n", ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 490) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 491) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 492) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 493) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 494) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 495) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 496) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=log&rev=%s\">log</a> \n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 497) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=diff&rev=%s\">diff</a>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 498) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 499) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 500) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 501) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=log&rev=%s\">log</a> \n", ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 502) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=diff&rev=%s\">diff</a>\n", ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 503) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 504) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 505) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 506) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 507) strbuf_addf( sb, " </div>\n\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 508) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 509)
bfc1508d (kx 2023-03-24 03:55:33 +0300 510) list = dlist_next( list );
bfc1508d (kx 2023-03-24 03:55:33 +0300 511) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 512) directories = tree_lines_free( directories );
bfc1508d (kx 2023-03-24 03:55:33 +0300 513) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 514)
bfc1508d (kx 2023-03-24 03:55:33 +0300 515) /**************************
bfc1508d (kx 2023-03-24 03:55:33 +0300 516) Print files:
bfc1508d (kx 2023-03-24 03:55:33 +0300 517) */
bfc1508d (kx 2023-03-24 03:55:33 +0300 518) if( files )
bfc1508d (kx 2023-03-24 03:55:33 +0300 519) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 520) struct dlist *list = files;
bfc1508d (kx 2023-03-24 03:55:33 +0300 521) while( list )
bfc1508d (kx 2023-03-24 03:55:33 +0300 522) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 523) struct tree_line *line = (struct tree_line *)list->data;
bfc1508d (kx 2023-03-24 03:55:33 +0300 524)
bfc1508d (kx 2023-03-24 03:55:33 +0300 525) if( line->name && line->size && line->revision && line->date )
bfc1508d (kx 2023-03-24 03:55:33 +0300 526) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 527) struct tm tm;
bfc1508d (kx 2023-03-24 03:55:33 +0300 528) time_t time = -1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 529) const char *query_string = ctx_remove_query_param( ctx.env.query_string, "rev" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 530) const char *exec = is_file_executable( relative_path, (const char *)line->name, rev );
bfc1508d (kx 2023-03-24 03:55:33 +0300 531)
bfc1508d (kx 2023-03-24 03:55:33 +0300 532) query_string = ctx_remove_query_param( query_string, "op" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 533)
bfc1508d (kx 2023-03-24 03:55:33 +0300 534) time = parse_date( &tm, (const char *)line->date );
bfc1508d (kx 2023-03-24 03:55:33 +0300 535)
bfc1508d (kx 2023-03-24 03:55:33 +0300 536) strbuf_addf( sb, " <div class=\"row\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 537) if( ctx.env.query_string && *ctx.env.query_string )
c7693c71 (kx 2023-04-12 19:21:06 +0300 538) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 539) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 540) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 541) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s/%s%s/%s/?%s\"><div class=\"tree-path file%s\">%s</div></a></div>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, ctx.env.query_string, exec, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 542) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 543) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 544) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 545) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s%s/%s/?%s\"><div class=\"tree-path file%s\">%s</div></a></div>\n", ctx.repo.name, path, line->name, ctx.env.query_string, exec, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 546) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 547) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 548) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 549) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 550) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 551) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 552) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s/%s%s/%s/\"><div class=\"tree-path file%s\">%s</div></a></div>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, exec, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 553) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 554) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 555) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 556) strbuf_addf( sb, " <div class=\"col-path\"><a href=\"/%s%s/%s/\"><div class=\"tree-path file%s\">%s</div></a></div>\n", ctx.repo.name, path, line->name, exec, line->name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 557) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 558) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 559) strbuf_addf( sb, " <div class=\"col-size\"><div onclick=\"trunc(this)\" class=\"tree-size trunc\">%s</div></div>\n", line->size );
bfc1508d (kx 2023-03-24 03:55:33 +0300 560) strbuf_addf( sb, " <div class=\"col-rev\"><div onclick=\"trunc(this)\" class=\"tree-rev trunc\">%s</div></div>\n", line->revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 561) if( time != -1 )
bfc1508d (kx 2023-03-24 03:55:33 +0300 562) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 563) strbuf_addf( sb, " <div class=\"col-date\"><div onclick=\"trunc(this)\" class=\"tree-date trunc\">" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 564) csvn_print_age( sb, time, 0, 0 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 565) strbuf_addf( sb, "</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 566) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 567) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 568) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 569) strbuf_addf( sb, " <div class=\"col-date\"><div onclick=\"trunc(this)\" class=\"tree-date trunc\">unknown</div></div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 570) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 571) strbuf_addf( sb, " <div class=\"col-links\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 572) strbuf_addf( sb, " <div onclick=\"trunc(this)\" class=\"tree-links trunc\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 573) if( query_string && *query_string )
bfc1508d (kx 2023-03-24 03:55:33 +0300 574) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 575) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 576) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 577) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=log&rev=%s&%s\">log</a> \n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 578) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=diff&rev=%s&%s\">diff </a>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 579) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=blame&rev=%s&%s\">blame</a>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 580) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 581) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 582) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 583) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=log&rev=%s&%s\">log</a> \n", ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 584) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=diff&rev=%s&%s\">diff </a>\n", ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 585) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=blame&rev=%s&%s\">blame</a>\n", ctx.repo.name, path, line->name, line->revision, query_string );
c7693c71 (kx 2023-04-12 19:21:06 +0300 586) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 587) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 588) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 589) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 590) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 591) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 592) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=log&rev=%s\">log</a> \n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 593) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=diff&rev=%s\">diff</a> \n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 594) strbuf_addf( sb, " <a href=\"/%s/%s%s/%s/?op=blame&rev=%s\">blame</a>\n", ctx.repo.repo_root, ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 595) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 596) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 597) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 598) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=log&rev=%s\">log</a> \n", ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 599) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=diff&rev=%s\">diff</a> \n", ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 600) strbuf_addf( sb, " <a href=\"/%s%s/%s/?op=blame&rev=%s\">blame</a>\n", ctx.repo.name, path, line->name, line->revision );
c7693c71 (kx 2023-04-12 19:21:06 +0300 601) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 602) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 603) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 604) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 605) strbuf_addf( sb, " </div>\n\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 606) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 607)
bfc1508d (kx 2023-03-24 03:55:33 +0300 608) list = dlist_next( list );
bfc1508d (kx 2023-03-24 03:55:33 +0300 609) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 610) files = tree_lines_free( files );
bfc1508d (kx 2023-03-24 03:55:33 +0300 611) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 612)
bfc1508d (kx 2023-03-24 03:55:33 +0300 613) strbuf_addf( sb, " </div> <!-- End of Tree -->\n\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 614)
bfc1508d (kx 2023-03-24 03:55:33 +0300 615) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 616) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 617)
bfc1508d (kx 2023-03-24 03:55:33 +0300 618) static void csvn_print_tree( struct strbuf *sb, const char *relative_path, int revision )
bfc1508d (kx 2023-03-24 03:55:33 +0300 619) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 620) const char *co_prefix = ctx.repo.checkout_ro_prefix;
c7693c71 (kx 2023-04-12 19:21:06 +0300 621) const char *name = ctx.repo.name;
c7693c71 (kx 2023-04-12 19:21:06 +0300 622) const char *repo_root = ctx.repo.repo_root;
bfc1508d (kx 2023-03-24 03:55:33 +0300 623) char *path = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 624)
bfc1508d (kx 2023-03-24 03:55:33 +0300 625) if( !sb ) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 626)
bfc1508d (kx 2023-03-24 03:55:33 +0300 627) if( relative_path && *relative_path )
bfc1508d (kx 2023-03-24 03:55:33 +0300 628) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 629) path = (char *)xmalloc( strlen( relative_path ) + 2 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 630) path[0] = '/';
bfc1508d (kx 2023-03-24 03:55:33 +0300 631) sprintf( (char *)&path[1], relative_path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 632) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 633) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 634) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 635) path = (char *)xmalloc( 1 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 636) path[0] = '\0';
bfc1508d (kx 2023-03-24 03:55:33 +0300 637) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 638)
bfc1508d (kx 2023-03-24 03:55:33 +0300 639) if( co_prefix )
bfc1508d (kx 2023-03-24 03:55:33 +0300 640) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 641) char repo_path[PATH_MAX] = { 0 };
c7693c71 (kx 2023-04-12 19:21:06 +0300 642) char cmd[PATH_MAX];
bfc1508d (kx 2023-03-24 03:55:33 +0300 643) struct strbuf buf = STRBUF_INIT;
bfc1508d (kx 2023-03-24 03:55:33 +0300 644) pid_t p = (pid_t) -1;
bfc1508d (kx 2023-03-24 03:55:33 +0300 645) int rc;
bfc1508d (kx 2023-03-24 03:55:33 +0300 646)
c7693c71 (kx 2023-04-12 19:21:06 +0300 647) if( repo_root && *repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 648) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 649) strcat( (char *)&repo_path[0], repo_root );
c7693c71 (kx 2023-04-12 19:21:06 +0300 650) strcat( (char *)&repo_path[0], "/" );
c7693c71 (kx 2023-04-12 19:21:06 +0300 651) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 652) strcat( (char *)&repo_path[0], name );
c7693c71 (kx 2023-04-12 19:21:06 +0300 653)
bfc1508d (kx 2023-03-24 03:55:33 +0300 654) if( revision )
bfc1508d (kx 2023-03-24 03:55:33 +0300 655) snprintf( (char *)&cmd[0], 1024,
bfc1508d (kx 2023-03-24 03:55:33 +0300 656) "svn list --revision %d --xml %s/%s%s 2>/dev/null",
c7693c71 (kx 2023-04-12 19:21:06 +0300 657) revision, co_prefix, (char *)&repo_path[0], path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 658) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 659) snprintf( (char *)&cmd[0], 1024,
bfc1508d (kx 2023-03-24 03:55:33 +0300 660) "svn list --xml %s/%s%s 2>/dev/null",
c7693c71 (kx 2023-04-12 19:21:06 +0300 661) co_prefix, (char *)&repo_path[0], path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 662) p = sys_exec_command( &buf, cmd );
bfc1508d (kx 2023-03-24 03:55:33 +0300 663) rc = sys_wait_command( p, NULL );
bfc1508d (kx 2023-03-24 03:55:33 +0300 664) if( rc != 0 )
bfc1508d (kx 2023-03-24 03:55:33 +0300 665) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 666) strbuf_release( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 667) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 668) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 669) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 670)
bfc1508d (kx 2023-03-24 03:55:33 +0300 671) xml_csvn_tree( (const struct strbuf *)&buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 672) strbuf_release( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 673)
bfc1508d (kx 2023-03-24 03:55:33 +0300 674) dlist_csvn_tree( sb, relative_path, revision );
bfc1508d (kx 2023-03-24 03:55:33 +0300 675) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 676)
bfc1508d (kx 2023-03-24 03:55:33 +0300 677) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 678) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 679) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 680)
bfc1508d (kx 2023-03-24 03:55:33 +0300 681) static void csvn_print_checkout_urls( struct strbuf *sb, const char *relative_path, int revision )
bfc1508d (kx 2023-03-24 03:55:33 +0300 682) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 683) char *path = NULL;
bfc1508d (kx 2023-03-24 03:55:33 +0300 684)
bfc1508d (kx 2023-03-24 03:55:33 +0300 685) if( !sb ) return;
bfc1508d (kx 2023-03-24 03:55:33 +0300 686)
bfc1508d (kx 2023-03-24 03:55:33 +0300 687) if( relative_path && *relative_path )
bfc1508d (kx 2023-03-24 03:55:33 +0300 688) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 689) path = (char *)xmalloc( strlen( relative_path ) + 2 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 690) path[0] = '/';
bfc1508d (kx 2023-03-24 03:55:33 +0300 691) sprintf( (char *)&path[1], relative_path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 692) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 693) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 694) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 695) path = (char *)xmalloc( 1 );
bfc1508d (kx 2023-03-24 03:55:33 +0300 696) path[0] = '\0';
bfc1508d (kx 2023-03-24 03:55:33 +0300 697) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 698)
bfc1508d (kx 2023-03-24 03:55:33 +0300 699) strbuf_addf( sb, " <div class=\"checkout-box\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 700) strbuf_addf( sb, " <div class=\"checkout-header\">Checkout</div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 701) strbuf_addf( sb, " <div class=\"checkout-urls\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 702) strbuf_addf( sb, " <div class=\"checkout-line\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 703) strbuf_addf( sb, " <div class=\"checkout-perms\">ro:</div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 704)
bfc1508d (kx 2023-03-24 03:55:33 +0300 705) if( revision )
c7693c71 (kx 2023-04-12 19:21:06 +0300 706) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 707) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 708) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 709) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout --revision %d %s/%s/%s%s</div>\n", revision, ctx.repo.checkout_ro_prefix, ctx.repo.repo_root, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 710) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 711) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 712) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 713) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout --revision %d %s/%s%s</div>\n", revision, ctx.repo.checkout_ro_prefix, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 714) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 715) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 716) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 717) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 718) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 719) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 720) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout %s/%s/%s%s</div>\n", ctx.repo.checkout_ro_prefix, ctx.repo.repo_root, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 721) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 722) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 723) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 724) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout %s/%s%s</div>\n", ctx.repo.checkout_ro_prefix, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 725) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 726) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 727)
bfc1508d (kx 2023-03-24 03:55:33 +0300 728) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 729) if( ctx.repo.checkout_prefix && *ctx.repo.checkout_prefix )
bfc1508d (kx 2023-03-24 03:55:33 +0300 730) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 731) strbuf_addf( sb, " <div class=\"checkout-line\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 732) strbuf_addf( sb, " <div class=\"checkout-perms\">rw:</div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 733)
bfc1508d (kx 2023-03-24 03:55:33 +0300 734) if( revision )
c7693c71 (kx 2023-04-12 19:21:06 +0300 735) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 736) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 737) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 738) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout --revision %d %s/%s/%s%s</div>\n", revision, ctx.repo.checkout_prefix, ctx.repo.repo_root, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 739) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 740) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 741) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 742) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout --revision %d %s/%s%s</div>\n", revision, ctx.repo.checkout_prefix, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 743) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 744) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 745) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 746) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 747) if( ctx.repo.repo_root && *ctx.repo.repo_root )
c7693c71 (kx 2023-04-12 19:21:06 +0300 748) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 749) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout %s/%s/%s%s</div>\n", ctx.repo.checkout_prefix, ctx.repo.repo_root, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 750) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 751) else
c7693c71 (kx 2023-04-12 19:21:06 +0300 752) {
c7693c71 (kx 2023-04-12 19:21:06 +0300 753) strbuf_addf( sb, " <div class=\"checkout-url\">svn checkout %s/%s%s</div>\n", ctx.repo.checkout_prefix, ctx.repo.name, path );
c7693c71 (kx 2023-04-12 19:21:06 +0300 754) }
c7693c71 (kx 2023-04-12 19:21:06 +0300 755) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 756)
bfc1508d (kx 2023-03-24 03:55:33 +0300 757) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 758) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 759) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 760) strbuf_addf( sb, " </div>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 761)
bfc1508d (kx 2023-03-24 03:55:33 +0300 762) free( path );
bfc1508d (kx 2023-03-24 03:55:33 +0300 763) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 764)
bfc1508d (kx 2023-03-24 03:55:33 +0300 765) void csvn_print_tree_page( void )
bfc1508d (kx 2023-03-24 03:55:33 +0300 766) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 767) FILE *fp;
bfc1508d (kx 2023-03-24 03:55:33 +0300 768) struct strbuf buf = STRBUF_INIT;
bfc1508d (kx 2023-03-24 03:55:33 +0300 769)
bfc1508d (kx 2023-03-24 03:55:33 +0300 770) fp = xfopen( ctx.page.header, "r" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 771) (void)strbuf_env_fread( &buf, fp );
bfc1508d (kx 2023-03-24 03:55:33 +0300 772) fclose( fp );
bfc1508d (kx 2023-03-24 03:55:33 +0300 773)
bfc1508d (kx 2023-03-24 03:55:33 +0300 774) strbuf_addf( &buf, " <div class=\"content segment\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 775) strbuf_addf( &buf, " <div class=\"container\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 776) strbuf_addf( &buf, " <div class=\"csvn-main-content\">\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 777)
bfc1508d (kx 2023-03-24 03:55:33 +0300 778) if( ctx.repo.relative_info.kind == KIND_DIR )
bfc1508d (kx 2023-03-24 03:55:33 +0300 779) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 780) if( ctx.repo.name )
bfc1508d (kx 2023-03-24 03:55:33 +0300 781) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 782) csvn_print_tree( &buf, ctx.repo.relative_path, ctx.query.rev );
bfc1508d (kx 2023-03-24 03:55:33 +0300 783) csvn_print_checkout_urls( &buf, ctx.repo.relative_path, ctx.query.rev );
bfc1508d (kx 2023-03-24 03:55:33 +0300 784) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 785) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 786) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 787) strbuf_addf( &buf, " <h1>Requested resource cannot be shown</h1>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 788) strbuf_addf( &buf, " <p class='leading'>Repository '%s' not found.</p>\n", ctx.repo.name );
bfc1508d (kx 2023-03-24 03:55:33 +0300 789) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 790) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 791) else
bfc1508d (kx 2023-03-24 03:55:33 +0300 792) {
bfc1508d (kx 2023-03-24 03:55:33 +0300 793) strbuf_addf( &buf, " <h1>Requested resource cannot be shown</h1>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 794) strbuf_addf( &buf, " <p class='leading'>This page assume the repository tree to be shown.</p>\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 795) }
bfc1508d (kx 2023-03-24 03:55:33 +0300 796)
bfc1508d (kx 2023-03-24 03:55:33 +0300 797) strbuf_addf( &buf, " </div> <!-- End of csvn-main-content -->\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 798) strbuf_addf( &buf, " </div> <!-- End of container -->\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 799) strbuf_addf( &buf, " </div> <!-- End of content segment -->\n" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 800)
bfc1508d (kx 2023-03-24 03:55:33 +0300 801) fp = xfopen( ctx.page.footer, "r" );
bfc1508d (kx 2023-03-24 03:55:33 +0300 802) (void)strbuf_env_fread( &buf, fp );
bfc1508d (kx 2023-03-24 03:55:33 +0300 803) fclose( fp );
bfc1508d (kx 2023-03-24 03:55:33 +0300 804)
bfc1508d (kx 2023-03-24 03:55:33 +0300 805) ctx.page.size = buf.len;
bfc1508d (kx 2023-03-24 03:55:33 +0300 806) csvn_print_http_headers();
bfc1508d (kx 2023-03-24 03:55:33 +0300 807) strbuf_write( &buf, STDOUT_FILENO );
bfc1508d (kx 2023-03-24 03:55:33 +0300 808) strbuf_release( &buf );
bfc1508d (kx 2023-03-24 03:55:33 +0300 809) }